diff --git a/.gitattributes b/.gitattributes
index a31f8ef74a2d13b6dafa64a4a15af618bb8115f1..2b719019847400287f9036ac2b84a5b5dabdf401 100644
--- a/.gitattributes
+++ b/.gitattributes
@@ -1,80 +1,4 @@
 * text=auto !eol
-/INSTALL -text
-/README.txt -text
-/build-all.sh -text
-centos_files/at-3.1.13-22.el7.x86_64.rpm -text
-centos_files/audit-2.6.5-3.el7_3.1.x86_64.rpm -text
-centos_files/audit-libs-2.6.5-3.el7_3.1.i686.rpm -text
-centos_files/audit-libs-2.6.5-3.el7_3.1.x86_64.rpm -text
-centos_files/bc-1.06.95-13.el7.x86_64.rpm -text
-centos_files/cpp-4.8.5-11.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/cracklib-2.9.0-11.el7.i686.rpm -text
-centos_files/cups-client-1.6.3-26.el7.x86_64.rpm -text
-centos_files/ed-1.9-4.el7.x86_64.rpm -text
-centos_files/gcc-c++-4.8.5-11.el7.x86_64.rpm -text
-centos_files/glibc-2.17-157.el7_3.1.i686.rpm -text
-centos_files/jq-1.5-1.el7.x86_64.rpm -text
-centos_files/kernel-headers-3.10.0-514.16.1.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/libcap-ng-0.7.5-4.el7.i686.rpm -text
-centos_files/libdb-5.3.21-19.el7.i686.rpm -text
-centos_files/libgcc-4.8.5-11.el7.i686.rpm -text
-centos_files/libgomp-4.8.5-11.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/libmpc-1.0.1-3.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/libpqxx-4.0.1-1.el7.x86_64.rpm -text
-centos_files/libselinux-2.5-6.el7.i686.rpm -text
-centos_files/libsepol-2.5-6.el7.i686.rpm -text
-centos_files/libstdc++-4.8.5-11.el7.i686.rpm -text
-centos_files/libstdc++-4.8.5-11.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/libstdc++-devel-4.8.5-11.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/m4-1.4.16-10.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/mailx-12.5-12.el7_0.x86_64.rpm -text
-centos_files/nasm-2.10.07-7.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/ncurses-libs-5.9-13.20130511.el7.i686.rpm -text
-centos_files/nspr-4.13.1-1.0.el7_3.i686.rpm -text
-centos_files/nss-3.28.4-1.0.el7_3.i686.rpm -text
-centos_files/nss-softokn-3.16.2.3-14.4.el7.i686.rpm -text
-centos_files/nss-softokn-freebl-3.16.2.3-14.4.el7.i686.rpm -text
-centos_files/nss-util-3.28.4-1.0.el7_3.i686.rpm -text
-centos_files/oniguruma-5.9.5-3.el7.x86_64.rpm -text
-centos_files/pam-1.1.8-18.el7.i686.rpm -text
-centos_files/pam-1.1.8-18.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/patch-2.7.1-8.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/pcre-8.32-15.el7_2.1.i686.rpm -text
-centos_files/pcre-8.32-15.el7_2.1.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/perl-Data-Dumper-2.145-3.el7.x86_64.rpm -text
-centos_files/perl-JSON-PP-2.27202-2.el7.noarch.rpm -text
-centos_files/postgresql-9.2.18-1.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/postgresql-contrib-9.2.18-1.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/postgresql-devel-9.2.18-1.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/postgresql-libs-9.2.18-1.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/postgresql-server-9.2.18-1.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/readline-6.2-9.el7.i686.rpm -text
-centos_files/redhat-lsb-core-4.1-27.el7.centos.1.i686.rpm -text
-centos_files/redhat-lsb-submod-security-4.1-27.el7.centos.1.i686.rpm -text
-centos_files/screen-4.1.0-0.23.20120314git3c2946.el7_2.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/spax-1.5.2-13.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/sqlite-3.7.17-8.el7.i686.rpm -text
-centos_files/time-1.7-45.el7.x86_64.rpm -text
-centos_files/uuid-1.6.2-26.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-centos_files/zlib-1.2.7-17.el7.i686.rpm -text
-centos_files/zlib-1.2.7-17.el7.x86_64.rpm -text svneol=unset#application/x-rpm
-/cfar_postgres_setup.sh -text
-/cfar_postgres_setup_for_other.sh -text
-/clean-all.sh -text
-/externals.conf -text
-/get-peasoup-packages.sh -text
-/irdb_vars -text
-/manifest.txt -text
-/postgres_setup.sh -text
-/regen_install.sh -text
-/set_command_envs -text
-/set_env_vars -text
-/set_ida_server -text
-/start_dev.sh -text
-ubuntu16_files/README.txt -text
-ubuntu16_files/Vagrantfile -text
-ubuntu16_files/generate_installer.sh -text
-ubuntu16_files/install.sh -text
-ubuntu16_files/manifest.txt -text
-ubuntu16_files/test.sh -text
-/yum_packages.sh -text
+irdb-libs/libcapstone norecurse
+irdb-libs/third_party/elfio-code norecurse
+
diff --git a/.gitignore b/.gitignore
index fe5c3b91e4ab99d537b6d1d5c9bcf8f28c5dd0eb..2a254052c20413600b15f34157f2917660a91ad2 100644
--- a/.gitignore
+++ b/.gitignore
@@ -4,4 +4,15 @@ ubuntu16_files/manifest.txt.config
 zest_runtime
 .sconsign.dblite
 build
-
+irdb-libs/build/
+irdb-libs/.sconsign.dblite
+irdb-libs/bin/
+irdb-libs/lib/
+irdb-libs/manifest.txt.config
+irdb-libs/tools/meds2pdb/meds2pdb
+irdb-libs/plugins_install/*.exe
+irdb-libs/plugins_install/*.so
+irdb-libs/*.swp
+irdb-libs/*.os
+irdb-libs/*.o
+scons_buiirdb-libs/ld
diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index 716c689e5b27a140dfc1c33754144807220a5e04..ff5de6fd1dd287858a9b75b75a3777a1f46a7bd1 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -1,8 +1,9 @@
 before_script:
   - "source ~gitlab-runner/cicd_support/cicd_support.shinc" 
 
+
 after_script:
-  - "source ~gitlab-runner/cicd_support/cicd_support.shinc" 
+  - "echo Test Complete."
 
 stages:
   - clean
@@ -18,20 +19,28 @@ stages:
   script:
     - ./cicd_testing/do-clean.sh 
 
+# per os items
 do-nightly-clean-ubuntu18:
   <<: *do-nightly-clean
   tags:
     - ubuntu18
+  variables:
+    OS: 'ubuntu18'  
 
 do-nightly-clean-ubuntu16:
   <<: *do-nightly-clean
   tags:
     - ubuntu16
+  variables:
+    OS: 'ubuntu16'  
 
 do-nightly-clean-centos75:
   <<: *do-nightly-clean
   tags:
     - centos75
+  variables:
+    OS: 'centos75'  
+
 
 #
 # Building
@@ -42,46 +51,43 @@ do-nightly-clean-centos75:
   script:
     - ./cicd_testing/do-build.sh 
 
-do-build-ubuntu18:
-  <<: *do-build
-  tags:
-    - ubuntu18
-
-do-build-ubuntu16:
-  <<: *do-build
-  tags:
-    - ubuntu16
+  variables:
+    OS: 'centos75'  
 
-do-build-centos75:
-  <<: *do-build
-  tags:
-    - centos75
 
 #
-# $PSZ ls
+# building 
 #
 
-.xform-ls: &xform-ls
-  stage: test
+
+# template
+.do-build: &do-build
+  stage: build
   script:
-    - ./cicd_testing/xform-ls.sh
+    - ./cicd_tests/do-build.sh
 
 
-xform-ls-ubuntu18:
-  <<: *xform-ls
+# per os items
+do-build-ubuntu18:
+  <<: *do-build
   tags:
     - ubuntu18
+  variables:
+    OS: 'ubuntu18'  
 
-xform-ls-ubuntu16:
-  <<: *xform-ls
+do-build-ubuntu16:
+  <<: *do-build
   tags:
     - ubuntu16
+  variables:
+    OS: 'ubuntu16'  
 
-xform-ls-centos75:
-  <<: *xform-ls
+do-build-centos75:
+  <<: *do-build
   tags:
     - centos75
-
+  variables:
+    OS: 'centos75'  
 
 
 #
@@ -90,7 +96,7 @@ xform-ls-centos75:
 .basic-pgms-rida: &eh-tests
   stage: test
   script:
-    - ./cicd_testing/eh-tests.sh
+    - ./irdb-libs/cicd_testing/eh-tests.sh
 
 eh-tests-ubuntu18:
   <<: *eh-tests
@@ -152,4 +158,36 @@ basic-pgms-fixcalls-centos75:
   <<: *basic-pgms-fixcalls
   tags:
     - centos75
+  variables:
+    OS: 'centos75'  
+
+#
+# elfdep test
+#
 
+# template
+.elfdep: &elfdep
+  stage: test
+  script:
+    - ./irdb-libs/cicd_tests/elfdep.sh
+
+elfdep-ubuntu18:
+  <<: *elfdep
+  tags:
+    - ubuntu18
+  variables:
+    OS: 'ubuntu18'  
+    
+elfdep-ubuntu16:
+  <<: *elfdep
+  tags:
+    - ubuntu16
+  variables:
+    OS: 'ubuntu16'  
+
+elfdep-centos75:
+  <<: *elfdep
+  tags:
+    - centos75
+  variables:
+    OS: 'centos75'  
diff --git a/.gitmodules b/.gitmodules
index 4becba678968bb674d225bb08572bc3848ca15ba..70eaa0970f863f7249f483f806bf20ff7c568096 100644
--- a/.gitmodules
+++ b/.gitmodules
@@ -54,3 +54,12 @@
 [submodule "irdb-sdk"]
 	path = irdb-sdk
 	url = git@git.zephyr-software.com:allnp/irdb-sdk.git
+[submodule "libcapstone"]
+	path = irdb-libs/libcapstone
+	url = https://github.com/aquynh/capstone.git
+[submodule "libehp"]
+	path = irdb-libs/libehp
+	url = git@git.zephyr-software.com:opensrc/libehp.git
+[submodule "third_party/elfio-code"]
+	path = irdb-libs/third_party/elfio-code
+	url = http://git.code.sf.net/p/elfio/code
diff --git a/irdb-lib/LICENSE.txt b/irdb-lib/LICENSE.txt
new file mode 100644
index 0000000000000000000000000000000000000000..312fba3fce32ba9e8a488ac58885ca41c59c2aa8
--- /dev/null
+++ b/irdb-lib/LICENSE.txt
@@ -0,0 +1,14 @@
+*************************************************************************************
+*
+* Unless otherwise specified, software artifacts in this directory and its
+* subdirectories are subject to:
+*
+* GOVERNMENT PURPOSE RIGHTS
+*
+* The Government's rights to use, modify, reproduce, release, perform, display, or
+* disclose this software are restricted by GOVERNMENT PURPOSE RIGHTS.
+*
+* Any reproduction of the software or portions thereof marked with this legend 
+* must also reproduce the markings.
+*
+*************************************************************************************
diff --git a/irdb-lib/README b/irdb-lib/README
new file mode 100644
index 0000000000000000000000000000000000000000..a0990367ef8b03c70c29d285e22ef85907e1d0b7
--- /dev/null
+++ b/irdb-lib/README
@@ -0,0 +1 @@
+TBD
diff --git a/irdb-lib/README.p1 b/irdb-lib/README.p1
new file mode 100644
index 0000000000000000000000000000000000000000..ba13e836d04b70852ad9101e2a2c0f492daa18c0
--- /dev/null
+++ b/irdb-lib/README.p1
@@ -0,0 +1,53 @@
+Note
+------------------
+20110622 To turn on P1 off the main trun, uncomment the comments in $PEASOUP_HOME/tools/ps_analyze.h that have to do with P1.
+
+Tool Chain
+------------------
+	MEDS: produces annotations
+	Grace: produces inputs/outputs, instruction execution trace
+	Stratafication: produces stratafied binary + heaprand + pc_confinement
+	P1: produces validated stratafied binary + SPRI file
+
+Steps in producing P1 transform rules
+-------------------------------------
+Call the p1transform tool
+	For every candidate function (i.e., not marketd as safe by MEDS, nice stack frame allocation/dealloc)
+	Generate assembly SPRI files for every candidate function in statically-linked program
+	Generate binary SPRI files for every candidate function in statically-linked program
+
+Produce coverage information for all candidate functions
+	Use instruction execution information provided by Grace + instructions info per function provided by MEDS/ELF (for a fn, metric is: #instructions-visited/#instructions-in-function). A better metric here could be: #instructions-stack-reference/#instruction-stack-references-in-function (TBD).
+
+Run BED (Behavioral Equivalence Detector)
+	Use GrammaTech's replayer tool
+
+Produce final set of spri rules by merging all functions that pass BED
+	Literally a merge of all the files
+
+Validate binary with final merged set of rules
+	Use BED again
+
+Deploy binary
+	If the validation fails, we leave the original binary alone, i.e., PEASOUP runs the stratafied binary but w/o any P1 transform rules
+	Otherwise, PEASOUP automatically picks up the P1 transform rules
+
+	NB: to do later: if validation fails we need to iterate and remove rules until we get a set of rules that pass BED. One way of doing this is to use coverage information to guide this search, i.e., start by removing the least covered functions first.
+
+Notes
+------------------
+P1 only attempts to transform functions that are "nice" (1 stack frame alloc/dealloc, not memory safe)
+   Example stats for test1.exe:
+         1027 functions, test1.exe(18), libc(1009)
+         P1 candidate fns (333)  P1 non-candidate (not "p1-nice") (584), non-candidate-MEDS-safe (110) 
+	 filtered-out functions(896) [no instruction coverage]
+	 P1 candidate functions(131) 
+	 BEDS(P1): 43/131 functions validated
+         #functions P1 transformed (43), libc(25), user-functions (13/18), MEDS safe:(4/18), main not transformed
+                
+P1 works by pattern matching to find and transform stack references. The set of rules is incomplete and probably does not handle corner cases 
+P1 only tested on simple test programs (test1, dumbledore), and with -fomit-frame-pointer
+
+Next steps
+------------------
+Push P1 through Spec2006. Find bugs. Fix them. Iterate.
diff --git a/irdb-lib/SConscript b/irdb-lib/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..22820a5b5594af3fa36121fb60aebe42fa589dc9
--- /dev/null
+++ b/irdb-lib/SConscript
@@ -0,0 +1,132 @@
+import shutil
+import os
+import tarfile
+
+Import('env')
+
+(sysname, nodename, release, version, machine)=os.uname()
+
+
+if env.GetOption('clean'):
+    if os.path.exists(os.environ['SECURITY_TRANSFORMS_HOME']+"/include/targ-config.h"):
+        print 'Removing include/targ-config.h'
+    	os.remove(os.environ['SECURITY_TRANSFORMS_HOME']+"/include/targ-config.h")
+    os.chdir(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone")
+    os.system("make clean")
+    if os.path.exists(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone/zipr_unpack"):
+    	shutil.rmtree(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone/zipr_unpack")
+    os.chdir(os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+else:
+
+    # check/install targ-config.h
+    #if not os.path.isfile(os.environ['SECURITY_TRANSFORMS_HOME']+"/include/targ-config.h"):
+	##print "uname=", sysname, " xx ", nodename, " xx ", release, " xx ", version, " xx ", machine
+	#shutil.copy( os.path.join(os.environ['SECURITY_TRANSFORMS_HOME'],"include",machine,"config.h"), 
+		     #os.path.join(os.environ['SECURITY_TRANSFORMS_HOME'],"include","targ-config.h"))
+
+    os.chdir(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone")
+    print "Rebuilding libcapstone."
+    jobs=env.GetOption('num_jobs')
+    os.system("make -j "+str(jobs))
+    os.chdir(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone")
+    if not os.path.exists(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone/zipr_unpack"):
+	    os.mkdir(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone/zipr_unpack")
+	    os.chdir(os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone/zipr_unpack")
+            print "Unpacking libcapstone.a for libIRDB-core."
+	    os.system("ar x "+os.environ['SECURITY_TRANSFORMS_HOME']+"/libcapstone/libcapstone.a")
+    os.chdir(os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+
+if "PEDI_HOME" in os.environ:
+	pedi = Command( target = "./testoutput",
+			source = "./SConscript",
+			action = os.environ['PEDI_HOME']+"/pedi -m manifest.txt " )
+
+env['BASE_IRDB_LIBS']="irdb-core", "pqxx", "pq"
+
+if sysname != "SunOS":
+	libPEBLISS=SConscript("pebliss/trunk/pe_lib/SConscript", variant_dir='scons_build/libPEBLISS')
+	# setup libraries needed for linking
+	env['BASE_IRDB_LIBS']=env['BASE_IRDB_LIBS']+("pebliss",)
+	if "PEDI_HOME" in os.environ:
+		Depends(pedi,libPEBLISS)
+
+# pebliss requires iconv, which needs to be explicit on cygwin.
+if "CYGWIN" in sysname:
+	# add tuple of 1 item!
+	env['BASE_IRDB_LIBS']=env['BASE_IRDB_LIBS']+("iconv",)
+
+Export('env')
+
+# get the libcapstone.so.[version] file regardless of the version extension
+libcapstone_path = Glob(os.environ['SECURITY_TRANSFORMS_HOME']+'/libcapstone/libcapstone.so.*')
+assert len(libcapstone_path) <= 1, "More than one candidate for libcapstone.so.[version]?!"
+
+libcapstone_path = env.Install("$SECURITY_TRANSFORMS_HOME/lib/", libcapstone_path)
+
+env.Command(os.environ['SECURITY_TRANSFORMS_HOME']+"/lib/libcapstone.so", libcapstone_path, "ln -s $SOURCE.abspath $TARGET.abspath")
+libcapstone=os.environ['SECURITY_TRANSFORMS_HOME']+"/lib/libcapstone.so"
+
+libehp=env.SConscript("libehp/SConscript", variant_dir='scons_build/libehp')
+libehp=env.Install("$SECURITY_TRANSFORMS_HOME/lib", libehp);
+
+libIRDBcore=env.SConscript("libIRDB-core/src/SConscript", variant_dir='scons_build/libIRDB-core')
+Depends(libIRDBcore,libcapstone)
+
+libIRDBcfg=env.SConscript("libIRDB-cfg/src/SConscript", variant_dir='scons_build/libIRDB-cfg')
+libIRDButil=env.SConscript("libIRDB-util/src/SConscript", variant_dir='scons_build/libIRDB-util')
+libIRDBsyscall=env.SConscript("libIRDB-syscall/src/SConscript", variant_dir='scons_build/libIRDB-syscall')
+libElfDep=SConscript("libIRDB-elfdep/src/SConscript", variant_dir='scons_build/libIRDB-elfdep')
+libtransform=SConscript("libIRDB-transform/src/SConscript", variant_dir='scons_build/libIRDB-transform')
+libEXEIO=SConscript("libEXEIO/SConscript", variant_dir='scons_build/libEXEIO')
+#libbea=SConscript("beaengine/SConscript", variant_dir='scons_build/beaengine')
+
+libMEDSannotation=SConscript("libMEDSannotation/SConscript", variant_dir='scons_build/libMEDSannotation')
+# libxform=SConscript("xform/SConscript", variant_dir='scons_build/libxform')
+# libIRDB=SConscript("libIRDB/SConscript", variant_dir='scons_build/libIRDB')
+# Depends(libIRDB,libcapstone)
+libStructDiv=SConscript("libStructDiv/SConscript", variant_dir='scons_build/libStructDiv')
+thanos=SConscript("thanos/SConscript", variant_dir='scons_build/thanos')
+rida=SConscript("rida/SConscript", variant_dir='scons_build/rida')
+meds2pdb=SConscript("meds2pdb/SConscript", variant_dir='scons_build/meds2pdb')
+dump_map=SConscript("dump_map/SConscript", variant_dir='scons_build/dump_map')
+dump_insns=SConscript("dump_insns/SConscript", variant_dir='scons_build/dump_insns')
+ir_builders=SConscript("ir_builders/SConscript", variant_dir='scons_build/ir_builders')
+
+
+# no more tools in irdb-libs
+#tools=None
+#if 'build_tools' not in env or env['build_tools'] is None or int(env['build_tools']) == 1:
+#	tools=SConscript("tools/SConscript", variant_dir='scons_build/tools')
+#	if "PEDI_HOME" in os.environ:
+#		Depends(pedi,tools)
+
+libs=( libIRDBcore, 
+	libIRDBcfg, 
+	libIRDButil, 
+	libIRDBcore, 
+	libehp,
+	libtransform,
+	libEXEIO,
+	libMEDSannotation,
+	libStructDiv,
+	libElfDep, 
+	libcapstone, 
+	thanos, 
+	rida, 
+	meds2pdb, 
+	dump_map, 
+	dump_insns, 
+	ir_builders)
+
+if "PEDI_HOME" in os.environ:
+	Depends(pedi,  libs)
+	Default( pedi )
+	Return('pedi')
+else:
+
+	Default(libIRDBcore, libIRDBcfg, libIRDButil, libIRDBdeep, libIRDBcore, libehp,libtransform,libEXEIO,libMEDSannotation,libStructDiv,libElfDep, libcapstone, thanos, rida, meds2pdb, dump_map, dump_insns, ir_builders)
+
diff --git a/irdb-lib/SConscript.deep b/irdb-lib/SConscript.deep
new file mode 100644
index 0000000000000000000000000000000000000000..93a9b58dfe7cccc9438a77ce455f05072efb0fd2
--- /dev/null
+++ b/irdb-lib/SConscript.deep
@@ -0,0 +1,16 @@
+import os
+
+Import('env')
+
+pedi = Command( target = "./testoutput",
+		source = "./SConscript",
+		action = os.environ['PEDI_HOME']+"/pedi -m manifest.txt " )
+
+env['BASE_IRDB_LIBS']="irdb-core", "pqxx", "pq"
+
+libIRDBdeep=env.SConscript("libIRDB-deep/src/SConscript", variant_dir='scons_build/libIRDB-deep')
+
+Depends(pedi,  libIRDBdeep)
+Default( pedi )
+
+Return('pedi')
diff --git a/irdb-lib/SConstruct b/irdb-lib/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..870baa527ce66caecdc36b2238b51008d243520b
--- /dev/null
+++ b/irdb-lib/SConstruct
@@ -0,0 +1,77 @@
+import os
+import sys
+
+
+
+(sysname, nodename, release, version, machine)=os.uname()
+
+env=Environment()
+
+
+# default build options
+env.Replace(CFLAGS="-fPIC  -fmax-errors=2 -Wall -Werror -fmax-errors=2")
+env.Replace(CXXFLAGS="-fPIC  -fmax-errors=2 -Wall -Werror -fmax-errors=2 ")
+env.Replace(LINKFLAGS="-fPIC -fmax-errors=2 -Wall -Werror -fmax-errors=2 ")
+
+# parse arguments into env and set default values.
+env.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+env.Replace(IRDB_SDK=os.environ['IRDB_SDK'])
+env.Replace(SMPSA_HOME=os.environ['SMPSA_HOME'])
+env.Replace(do_64bit_build=ARGUMENTS.get("do_64bit_build",None))
+env.Replace(debug=ARGUMENTS.get("debug",0))
+env.Replace(build_deep=ARGUMENTS.get("build_deep", 0))
+env.Replace(build_tools=ARGUMENTS.get("build_tools", 1))
+env.Replace(build_stars=ARGUMENTS.get("build_stars", 1))
+env.Replace(build_cgc=ARGUMENTS.get("build_cgc", 0))
+
+if 'PEDI_HOME' in os.environ:
+	env.Replace(PEDI_HOME=os.environ['PEDI_HOME'])
+
+env.Append(LINKFLAGS=" -Wl,-unresolved-symbols=ignore-in-shared-libs ")
+
+if int(env['debug']) == 1:
+        print "Setting debug mode"
+        env.Append(CFLAGS=" -g ")
+        env.Append(CXXFLAGS=" -g ")
+	env.Append(LINKFLAGS=" -g ")
+	env.Append(SHLINKFLAGS=" -g ")
+else:
+        print "Setting release mode"
+        env.Append(CFLAGS=" -O3 ")
+        env.Append(CXXFLAGS=" -O3 ")
+        env.Append(LINKFLAGS=" -O3  ")
+        env.Append(SHLINKFLAGS=" -O3  ")
+
+# set 32/64 bit build properly
+print  "env[64bit]="+str(env['do_64bit_build'])
+if env['do_64bit_build'] is None:
+	print 'Defaulting to default compilation size.'
+elif int(env['do_64bit_build']) == 1:
+	print 'Using 64-bit compilation size.'
+        env.Append(CFLAGS=" -m64 ")
+        env.Append(CXXFLAGS=" -m64 ")
+        env.Append(LINKFLAGS=" -m64 ")
+        env.Append(SHLINKFLAGS=" -m64 ")
+else:
+	print 'Using 32-bit compilation size.'
+        env.Append(CFLAGS=" -m32 ")
+        env.Append(CXXFLAGS=" -m32 ")
+        env.Append(LINKFLAGS=" -m32 ")
+        env.Append(SHLINKFLAGS=" -m32 ")
+
+
+
+# add extra flag for solaris.
+if sysname == "SunOS":
+        env.Append(LINKFLAGS=" -L/opt/csw/lib -DSOLARIS  ")
+        env.Append(SHLINKFLAGS=" -L/opt/csw/lib -DSOLARIS  ")
+        env.Append(CFLAGS=" -I/opt/csw/include -DSOLARIS ")
+        env.Append(CXXFLAGS=" -I/opt/csw/include -DSOLARIS  ")
+
+
+Export('env')
+if int(env['build_deep']) == 1:
+	SConscript("SConscript.deep", variant_dir='build')
+else:
+	SConscript("SConscript", variant_dir='build')
+
diff --git a/irdb-lib/bin/.ignore b/irdb-lib/bin/.ignore
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/irdb-lib/cicd_tests/do-build.sh b/irdb-lib/cicd_tests/do-build.sh
new file mode 100755
index 0000000000000000000000000000000000000000..facd61a68834f2eb43e8882cd2fcbe27da134fb3
--- /dev/null
+++ b/irdb-lib/cicd_tests/do-build.sh
@@ -0,0 +1,40 @@
+#/bin/bash 
+
+set -e
+set -x
+
+main()
+{
+
+	# gather info for debugging later, probably not necessary 
+	pwd
+	hostname
+	whoami
+	env|grep "^CICD"
+
+	git submodule sync 
+	git submodule update --init --recursive
+
+	local orig_dir=$(pwd)
+
+	# puts irdblibs_umbrella (and all submodules) in CICD_MODULE_WORK_DIR
+	cicd_setup_module_dependency allnp/peasoup_umbrella.git irdblibs_umbrella
+
+
+	# puts the version of irdb-libs to test in irdblibs_umbrella/irdb-libs
+	cicd_put_module_in_tree irdblibs_umbrella/irdb-libs
+
+	# Build/run $PSZ, test result
+	cd $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+	source set_env_vars
+	sudo ./get-peasoup-packages.sh all
+
+	# remove pedi files so that rebuilding includes re-doing pedi setup.
+	$PEDI_HOME/pedi -c -m manifest.txt || true # ignore errors in cleanup
+	./build-all.sh
+	dropdb $PGDATABASE 2>/dev/null || true ; ./postgres_setup.sh
+
+	cd $orig_dir
+}
+
+main "$@"
diff --git a/irdb-lib/cicd_tests/do-clean.sh b/irdb-lib/cicd_tests/do-clean.sh
new file mode 100755
index 0000000000000000000000000000000000000000..940af5a554ef70271942e838f8cecd03e1859922
--- /dev/null
+++ b/irdb-lib/cicd_tests/do-clean.sh
@@ -0,0 +1,22 @@
+#/bin/bash 
+
+set -e
+set -x
+
+main()
+{
+
+	# gather info for debugging later, probably not necessary 
+	pwd
+	hostname
+	whoami
+	env|grep "^CICD"
+
+
+	if [[ $CICD_NIGHTLY == 1 ]] ; then
+		rm -rf $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+	fi
+
+}
+
+main "$@"
diff --git a/irdb-lib/cicd_tests/elfdep.sh b/irdb-lib/cicd_tests/elfdep.sh
new file mode 100755
index 0000000000000000000000000000000000000000..81c3f7840af9d48a5ce27729e1df89d45cd6ca1e
--- /dev/null
+++ b/irdb-lib/cicd_tests/elfdep.sh
@@ -0,0 +1,9 @@
+#!/bin/bash
+set -e
+set -x
+
+cd $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+source set_env_vars
+
+cd $SECURITY_TRANSFORMS_HOME/libIRDB-elfdep/test/
+./test-elfdep.sh
diff --git a/irdb-lib/cicd_tests/test_fib.sh b/irdb-lib/cicd_tests/test_fib.sh
new file mode 100755
index 0000000000000000000000000000000000000000..f2e487cd70d6b4058085e5dfd586d165010c9644
--- /dev/null
+++ b/irdb-lib/cicd_tests/test_fib.sh
@@ -0,0 +1,127 @@
+#!/bin/bash  
+
+set -e
+trap clean EXIT
+
+cd $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+source set_env_vars
+cd ./irdb-libs/tools/selective_cfi/tests/cicd_tests/fib_src
+
+source ../../cfi_smokescreen_configs.sh
+
+get_correct()
+{
+	cp libfib.so.orig libfib.so
+	cp libfib2.so.orig libfib2.so
+	# for fib.exe, a non-zero exit status can indicate success
+	set +e
+	./fib.exe $1 > correct
+	echo $? >> correct
+	set -e
+}
+
+do_test()
+{
+	echo running test $1 $2 $3 $4
+	
+	n=$2
+
+	get_correct $n
+
+	cp $3 libfib.so  
+	cp $4 libfib2.so 
+	# for fib.exe, a non-zero exit status can indicate success
+	set +e
+	./$1 $n > out 
+	echo $? >> out
+
+
+	cmp out correct
+	res=$?
+	if [[ $res != 0 ]]; then
+		echo "detected output diff:"
+		diff out correct
+		exit 1
+	fi
+
+	set -e
+}
+
+
+build()
+{
+	gcc -o libfib.so libfib.c -w -shared -fPIC
+	gcc -o libfib2.so libfib2.c -w -shared -fPIC
+	gcc -o fib.exe fib.c -w -L. -lfib -lfib2
+	gcc -o fib.exe.pie fib.c -fPIC -fpie -pie -w -L. -lfib -lfib2
+	mv libfib.so libfib.so.orig
+	mv libfib2.so libfib2.so.orig
+}
+
+
+protect()
+{
+	files=(libfib.so.orig libfib2.so.orig fib.exe fib.exe.pie)
+
+	libfib_so_orig_varients=(libfib.so.orig)
+	libfib2_so_orig_varients=(libfib2.so.orig)
+	fib_exe_varients=(fib.exe)
+	fib_exe_pie_varients=(fib.exe.pie)	
+ 
+        for file in "${files[@]}"; do
+                for config in "${configs[@]}"; do
+                        echo Protecting file "$file" with config "$config"
+			set +e
+                        "$config" ./"$file" ./"$file"".""$config" > out 2>&1 
+			res=$?
+			set -e
+			if [[ $res == 0 ]]; then
+				rm -rf out peasoup*
+			else
+				echo "Failed protection!"
+				cat out peasoup*/logs/*
+				exit 1
+			fi
+                        varient_array_name="$(echo "$file" | sed -e 's/\./_/g')""_varients"
+			varient_file="$file"".""$config"
+                        eval $varient_array_name+=\(\$varient_file\)                        
+                done
+        done	
+}
+
+clean()
+{
+	local ec=$?
+	rm -f out >> /dev/null 2>&1
+	rm -f correct >> /dev/null 2>&1
+	rm -Rf fib.exe* peasoup_exe* lib*.so* >> /dev/null 2>&1
+
+ 	for config in "${configs[@]}"; do
+                rm -f *."$config" >> /dev/null 2>&1 
+        done	
+	exit $ec
+}
+
+
+main()
+{
+	build
+	protect
+
+	fib_varients=("${fib_exe_varients[@]}" "${fib_exe_pie_varients[@]}")
+
+	for fib_varient in "${fib_varients[@]}"; do
+                for libfib_varient in "${libfib_so_orig_varients[@]}"; do
+			for libfib2_varient in "${libfib2_so_orig_varients[@]}"; do
+				for i in 2 6; do
+                        		do_test "$fib_varient" $i "$libfib_varient" "$libfib2_varient"
+				done
+			done
+                done
+        done
+	
+	exit 0	
+}
+
+
+main $*
diff --git a/irdb-lib/cicd_tests/test_foo.sh b/irdb-lib/cicd_tests/test_foo.sh
new file mode 100755
index 0000000000000000000000000000000000000000..77ae98d69679c6db8cf424ce674b6904bcb373b3
--- /dev/null
+++ b/irdb-lib/cicd_tests/test_foo.sh
@@ -0,0 +1,129 @@
+#!/bin/bash
+
+set -e
+trap clean EXIT
+
+cd $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+source set_env_vars
+cd ./irdb-libs/tools/selective_cfi/tests/cicd_tests/foo_src
+
+source ../../cfi_smokescreen_configs.sh 
+
+get_correct()
+{
+	cp libfoo.so.orig libfoo.so
+	./foo.exe > correct
+	echo $? >> correct
+}
+
+do_test()
+{
+	echo Running test: "$1" "$2"
+	
+	set +e
+	cp $2 libfoo.so  
+	./$1 > out 
+	echo $? >> out
+
+	cmp out correct
+        res=$?
+        if [[ $res != 0 ]]; then
+                echo "detected output diff:"
+                diff out correct
+                exit 1
+        fi
+	set -e
+
+}
+
+
+build()
+{
+	gcc -o libfoo.so libfoo.c -w -shared -fPIC
+	gcc -o foo.exe foo.c -w -L. -lfoo
+	mv libfoo.so libfoo.so.orig
+
+	gcc -o libfoo.O.so libfoo.c -O -w -shared -fPIC
+        gcc -o libfoo.O2.so libfoo.c -O2 -w -shared -fPIC
+        gcc -o libfoo.O3.so libfoo.c -O3 -w -shared -fPIC
+        gcc -o libfoo.Os.so libfoo.c -Os -w -shared -fPIC
+        mv libfoo.O.so libfoo.O.so.orig
+        mv libfoo.O2.so libfoo.O2.so.orig
+        mv libfoo.O3.so libfoo.O3.so.orig
+        mv libfoo.Os.so libfoo.Os.so.orig
+}
+
+
+protect()
+{
+	files=(foo.exe libfoo.so.orig libfoo.O.so.orig libfoo.O2.so.orig libfoo.O3.so.orig libfoo.Os.so.orig)
+
+	foo_exe_varients=(foo.exe)
+	libfoo_so_orig_varients=(libfoo.so.orig)
+	libfoo_O_so_orig_varients=(libfoo.O.so.orig)
+        libfoo_O2_so_orig_varients=(libfoo.O2.so.orig)
+        libfoo_O3_so_orig_varients=(libfoo.O3.so.orig)
+        libfoo_Os_so_orig_varients=(libfoo.Os.so.orig)
+		
+ 	for file in "${files[@]}"; do
+		for config in "${configs[@]}"; do
+			echo Protecting file "$file" with config "$config"
+			set -e
+			"$config" ./"$file" ./"$file"".""$config"  > ps.log 2>&1 
+			res=$?
+			set +e
+			if [[ $res  != 0 ]]; then
+				echo "Failed to xform!"
+				cat peasoup*/logs/*
+				exit 1	
+			else
+				rm -Rf peasoup*
+			fi
+			
+			varient_array_name="$(echo "$file" | sed -e 's/\./_/g')""_varients"
+			varient_file="$file"".""$config"
+                        eval $varient_array_name+=\(\$varient_file\)			
+		done	
+	done
+	
+}
+
+clean()
+{
+	local ec=$?
+	rm -f out >> /dev/null 2&>1
+	rm -f correct >> /dev/null 2&>1
+	rm -rf peasoup_executable_directory.* >> /dev/null 2&>1
+	rm -f *.orig >> /dev/null 2&>1
+	rm -f *.exe >> /dev/null 2&>1
+	rm -f *.so >> /dev/null 2&>1
+	
+	for config in "${configs[@]}"; do
+		rm -f *."$config" >> /dev/null 2&>1
+	done
+	
+	exit $ec
+}
+
+
+main()
+{
+	build
+	protect
+	get_correct
+
+	libfoo_varients=("${libfoo_so_orig_varients[@]}" "${libfoo_O_so_orig_varients[@]}" "${libfoo_O2_so_orig_varients[@]}"
+                         "${libfoo_O3_so_orig_varients[@]}" "${libfoo_Os_so_orig_varients[@]}")
+
+	
+	for foo_varient in "${foo_exe_varients[@]}"; do
+		for libfoo_varient in "${libfoo_varients[@]}"; do
+			do_test "$foo_varient" "$libfoo_varient"
+		done
+	done	
+	
+	exit 0
+}
+
+
+main $*
diff --git a/irdb-lib/cicd_tests/xform-cat.sh b/irdb-lib/cicd_tests/xform-cat.sh
new file mode 100755
index 0000000000000000000000000000000000000000..4ee04a86db0c6c2776626dcd25414d00915e3089
--- /dev/null
+++ b/irdb-lib/cicd_tests/xform-cat.sh
@@ -0,0 +1,11 @@
+cd $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+
+set -e
+set -x
+
+source set_env_vars
+cd /tmp
+rm -rf cat.rida ped_cat; 
+$PSZ $(which cat) ./cat.rida -c rida=on -s meds_static=off -c p1transform=on --tempdir ped_cat || true
+if [[ ! -x ./cat.rida ]]; then cat ped_cat/logs/*; fi
+./cat.rida /dev/null 
diff --git a/irdb-lib/cicd_tests/xform-ls.sh b/irdb-lib/cicd_tests/xform-ls.sh
new file mode 100755
index 0000000000000000000000000000000000000000..f31df7b4023e81619efa86fb57d12b6574b5664d
--- /dev/null
+++ b/irdb-lib/cicd_tests/xform-ls.sh
@@ -0,0 +1,12 @@
+#!/bin/bash
+set -e
+set -x
+
+cd $CICD_MODULE_WORK_DIR/irdblibs_umbrella
+source set_env_vars
+cd /tmp
+rm -rf ls.rida ped_ls
+$PSZ /bin/ls ./ls.rida -c rida=on -s meds_static=off -c p1transform=on --tempdir ped_ls || true
+if [[ ! -x ./ls.rida ]]; then cat ped_ls/logs/*; fi
+rm -rf ped_ls
+./ls.rida
diff --git a/irdb-lib/dump_insns/Makefile.in b/irdb-lib/dump_insns/Makefile.in
new file mode 100644
index 0000000000000000000000000000000000000000..521dc2c07323f832d457aae0085a8e59c89f1858
--- /dev/null
+++ b/irdb-lib/dump_insns/Makefile.in
@@ -0,0 +1,42 @@
+
+
+PROGS=fix_rets.exe
+
+CXX=@CXX@
+CXXFLAGS= 
+INCLUDE=-I. -I../include -I../xform -I../../beaengine/include -I../../libIRDB/include/ -I../../libMEDSannotation/include/ -I../libtransform/include/ -I../transforms
+CXXFLAGS= @EXTRA_CXXFLAGS@ $(INCLUDE) -Wall
+LIBS=-L../../lib -lxform -lIRDB-core -lIRDB-cfg -lBeaEngine_s_d -lpqxx  -lMEDSannotation -ltransform -lpq
+
+
+OBJS=fix_rets.o fix_rets_driver.o
+programs=fix_rets.exe
+
+.SUFFIXES: .o .c .exe .cpp .hpp
+
+all: $(programs)
+	@echo "---------------------------------------------"
+	@echo "- Fix Rets directory -- Build complete -"
+	@echo "---------------------------------------------"
+
+
+-include $(OBJS:.o=.d)
+
+%.o: %.cpp
+	$(CXX) -c  $(CXXFLAGS) $*.cpp 
+	@#
+	@# build dependencies --  http://scottmcpeak.com/autodepend/autodepend.html
+	@#
+	@cpp -M $(CXXFLAGS) $*.cpp > $*.d || true 
+	@cp -f $*.d $*.d.tmp
+	@sed -e 's/.*://' -e 's/\\$$//' < $*.d.tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $*.d
+	@rm -f $*.d.tmp
+	
+clean:
+	rm -f *.o core *.exe
+
+$(programs): ../../lib/*.a
+
+fix_rets.exe:   $(OBJS)
+	$(CXX) $(CXXFLAGS) $^ $(INCLUDE) $(LIBS) -o $@
+
diff --git a/irdb-lib/dump_insns/SConscript b/irdb-lib/dump_insns/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..a087b1bb3ea468eecca4f5a555bbbcce1f73306d
--- /dev/null
+++ b/irdb-lib/dump_insns/SConscript
@@ -0,0 +1,28 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+cpppath=''' 
+	 $IRDB_SDK/include 
+	'''
+
+
+files=Glob( Dir('.').srcnode().abspath+"/*.cpp")
+
+myenv.Append(CPPFLAGS="-std=c++11")
+
+
+pgm="dump_insns.exe"
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split( env.subst('$BASE_IRDB_LIBS')+ "  irdb-cfg irdb-util irdb-transform ") 
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+pgm=myenv.Program(pgm,  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+#install=myenv.Install("$SECURITY_TRANSFORMS_HOME/bin/", pgm)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install/", pgm)
+Default(install)
+Return('install')
diff --git a/irdb-lib/dump_insns/SConstruct b/irdb-lib/dump_insns/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..17f632b8c29cd420163897b1eb044ca3486df362
--- /dev/null
+++ b/irdb-lib/dump_insns/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+install=SConscript("SConscript")
+Return('install')
diff --git a/irdb-lib/dump_insns/dump_insns.cpp b/irdb-lib/dump_insns/dump_insns.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a51b71f075f94bcbf23ab525dc336ecce1c1d2f5
--- /dev/null
+++ b/irdb-lib/dump_insns/dump_insns.cpp
@@ -0,0 +1,125 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <stdlib.h>
+#include <fstream>
+#include <irdb-core>
+#include <libgen.h>
+#include <iomanip>
+#include <algorithm>
+
+
+using namespace std;
+using namespace IRDB_SDK;
+
+void usage(char* name)
+{
+	cerr<<"Usage: "<<name<<" <variant_id>\n"; 
+}
+
+
+
+int main(int argc, char **argv)
+{
+        if(argc != 2)
+        {
+                usage(argv[0]);
+                exit(1);
+        }
+
+
+        string programName(argv[0]);
+        int variantID = atoi(argv[1]);
+
+
+        /* setup the interface to the sql server */
+        auto pqxx_interface=pqxxDB_t::factory();
+        BaseObj_t::setInterface(pqxx_interface.get());
+
+        auto pidp=VariantID_t::factory(variantID);
+        assert(pidp->isRegistered()==true);
+
+
+
+        bool one_success = false;
+        for(set<File_t*>::iterator it=pidp->getFiles().begin();
+            it!=pidp->getFiles().end();
+                ++it)
+        {
+                File_t* this_file = *it;
+                try
+                {
+                	auto firp = FileIR_t::factory(pidp.get(), this_file);
+
+                	assert(firp && pidp);
+
+			for(auto insn : firp->getInstructions())
+			{
+				assert(insn);
+				const auto p_d=DecodedInstruction_t::factory(insn);
+				const auto &d=*p_d;
+				const auto &operands=d.getOperands();
+
+				cout<<" "<<d.getDisassembly()<<endl;
+				int op_count=0;
+				for(const auto p_op : operands)
+				{
+					const auto &op=*p_op;
+					auto readWriteString= string();
+					if(op.isRead()) readWriteString += "READ ";
+					if(op.isWritten()) readWriteString += "WRITE ";
+
+					cout<<"\t"<<"operand["<<op_count<<"]="<<op.getString() << boolalpha 
+					    <<" rw="     <<readWriteString
+					    <<" isGPReg="<<op.isGeneralPurposeRegister()
+					    <<" isMem="  <<op.isMemory()
+					    <<" isImm="  <<op.isConstant() 
+					    <<" isPcrel="<<op.isPcrel() 
+					    << endl;
+	
+					op_count++;			
+				}
+				
+	
+			}
+
+
+
+                }
+                catch (DatabaseError_t pnide)
+                {
+                        cerr << programName << ": Unexpected database error: " << pnide << "file url: " << this_file->getURL() << endl;
+                }
+                catch (...)
+                {
+                        cerr << programName << ": Unexpected error file url: " << this_file->getURL() << endl;
+                }
+        } // end file iterator
+
+        // if any integer transforms for any files succeeded, we commit
+        if (one_success)
+	{
+		cout<<"Commiting changes...\n";
+                pqxx_interface->commit();
+	}
+
+        return 0;
+}
+
diff --git a/irdb-lib/dump_map/Makefile.in b/irdb-lib/dump_map/Makefile.in
new file mode 100644
index 0000000000000000000000000000000000000000..521dc2c07323f832d457aae0085a8e59c89f1858
--- /dev/null
+++ b/irdb-lib/dump_map/Makefile.in
@@ -0,0 +1,42 @@
+
+
+PROGS=fix_rets.exe
+
+CXX=@CXX@
+CXXFLAGS= 
+INCLUDE=-I. -I../include -I../xform -I../../beaengine/include -I../../libIRDB/include/ -I../../libMEDSannotation/include/ -I../libtransform/include/ -I../transforms
+CXXFLAGS= @EXTRA_CXXFLAGS@ $(INCLUDE) -Wall
+LIBS=-L../../lib -lxform -lIRDB-core -lIRDB-cfg -lBeaEngine_s_d -lpqxx  -lMEDSannotation -ltransform -lpq
+
+
+OBJS=fix_rets.o fix_rets_driver.o
+programs=fix_rets.exe
+
+.SUFFIXES: .o .c .exe .cpp .hpp
+
+all: $(programs)
+	@echo "---------------------------------------------"
+	@echo "- Fix Rets directory -- Build complete -"
+	@echo "---------------------------------------------"
+
+
+-include $(OBJS:.o=.d)
+
+%.o: %.cpp
+	$(CXX) -c  $(CXXFLAGS) $*.cpp 
+	@#
+	@# build dependencies --  http://scottmcpeak.com/autodepend/autodepend.html
+	@#
+	@cpp -M $(CXXFLAGS) $*.cpp > $*.d || true 
+	@cp -f $*.d $*.d.tmp
+	@sed -e 's/.*://' -e 's/\\$$//' < $*.d.tmp | fmt -1 | sed -e 's/^ *//' -e 's/$$/:/' >> $*.d
+	@rm -f $*.d.tmp
+	
+clean:
+	rm -f *.o core *.exe
+
+$(programs): ../../lib/*.a
+
+fix_rets.exe:   $(OBJS)
+	$(CXX) $(CXXFLAGS) $^ $(INCLUDE) $(LIBS) -o $@
+
diff --git a/irdb-lib/dump_map/SConscript b/irdb-lib/dump_map/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..8eaf74bbfcb93d2087ada4d39f0a731348dc235e
--- /dev/null
+++ b/irdb-lib/dump_map/SConscript
@@ -0,0 +1,28 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+cpppath=''' 
+	 $IRDB_SDK/include 
+	'''
+
+
+files=Glob( Dir('.').srcnode().abspath+"/*.cpp")
+
+myenv.Append(CPPFLAGS="-std=c++11")
+
+
+pgm="dump_map.exe"
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split( env.subst('$BASE_IRDB_LIBS')+ "  irdb-cfg irdb-util irdb-transform ") 
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+pgm=myenv.Program(pgm,  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+#install=myenv.Install("$SECURITY_TRANSFORMS_HOME/bin/", pgm)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install/", pgm)
+Default(install)
+Return('install')
diff --git a/irdb-lib/dump_map/SConstruct b/irdb-lib/dump_map/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..17f632b8c29cd420163897b1eb044ca3486df362
--- /dev/null
+++ b/irdb-lib/dump_map/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+install=SConscript("SConscript")
+Return('install')
diff --git a/irdb-lib/dump_map/dump_map.cpp b/irdb-lib/dump_map/dump_map.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e9d996a857e6f293119a16e8fc91d29df6f2847c
--- /dev/null
+++ b/irdb-lib/dump_map/dump_map.cpp
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <stdlib.h>
+#include <fstream>
+#include <irdb-core>
+#include <libgen.h>
+#include <iomanip>
+#include <algorithm>
+
+
+using namespace std;
+using namespace IRDB_SDK;
+
+void usage(char* name)
+{
+	cerr<<"Usage: "<<name<<" <variant_id>\n"; 
+}
+
+
+void dump_icfs(Instruction_t* insn)
+{
+	if(insn->getIBTargets()==NULL)	
+		return;	
+	
+	cout<<"\tComplete: "<<boolalpha<<insn->getIBTargets()->isComplete()<<endl;
+	cout<<"\tModComplete: "<<boolalpha<<insn->getIBTargets()->isModuleComplete()<<endl;
+	cout<<"\tTargets: "<<endl;
+	for_each(insn->getIBTargets()->begin(), insn->getIBTargets()->end(), [&](const Instruction_t* targ)
+	{
+		const auto d=DecodedInstruction_t::factory(targ);
+		cout<<"\t"<<targ->getBaseID()<<":"<<d->getDisassembly()<<endl;
+	});
+}
+
+int main(int argc, char **argv)
+{
+        if(argc != 2)
+        {
+                usage(argv[0]);
+                exit(1);
+        }
+
+	auto dump_icfs_flag=(DatabaseID_t)BaseObj_t::NOT_IN_DATABASE; 
+	auto dump_icfs_str=getenv("DUMP_ICFS");
+	if(dump_icfs_str)
+		dump_icfs_flag=(DatabaseID_t)strtoull(dump_icfs_str,NULL,0);
+		
+
+        string programName(argv[0]);
+        int variantID = atoi(argv[1]);
+
+        /* setup the interface to the sql server */
+        auto pqxx_interface=pqxxDB_t::factory();
+        BaseObj_t::setInterface(pqxx_interface.get());
+
+        auto pidp=VariantID_t::factory(variantID);
+        assert(pidp->isRegistered()==true);
+
+
+
+        bool one_success = false;
+        for(set<File_t*>::iterator it=pidp->getFiles().begin();
+            it!=pidp->getFiles().end();
+                ++it)
+        {
+                File_t* this_file = *it;
+                try
+                {
+                	auto firp = FileIR_t::factory(pidp.get(), this_file);
+	
+			cout<<"file: "<<this_file->getURL()<<endl;
+			cout<<setw(9)<<"ID"<<" "
+			    <<setw(10)<<"Addr."<<" "
+			    <<setw(10)<<"IBTA"<<" "
+			    <<setw(9)<<"FT ID"<<" "
+			    <<setw(9)<<"TargID"<<" "
+			    <<setw(9)<<"Func"<<" "
+			    <<"Disassembly"<< endl;
+
+                	assert(firp && pidp);
+
+			for(auto it=firp->getInstructions().begin(); it!=firp->getInstructions().end(); ++it)
+			{
+				Instruction_t* insn=*it;
+				assert(insn);
+				cout<<hex<<setw(9)<<insn->getBaseID()<<" "<<hex<<setw(10)<<insn->getAddress()->getVirtualOffset();
+				
+				cout<<" "<<hex<<setw(10)<<
+					(insn->getIndirectBranchTargetAddress() ? 
+						insn->getIndirectBranchTargetAddress()->getVirtualOffset() :
+						0
+					)
+				    <<" ";
+				cout<<hex<<setw(9)<<(insn->getFallthrough()  ? insn->getFallthrough()->getBaseID() : -1) << " ";
+				cout<<hex<<setw(9)<<(insn->getTarget()  ? insn->getTarget()->getBaseID() : -1) << " ";
+				if(insn->getFunction() && insn->getFunction()->getEntryPoint())
+					cout<<hex<<setw(9)<<insn->getFunction()->getEntryPoint()->getBaseID();
+				else
+					cout<<setw(9)<<"NoFunc";
+					
+				const auto d=DecodedInstruction_t::factory(insn);
+				cout<<" "<<d->getDisassembly()<<"("<<insn->getComment()<<")"<<endl;
+	
+				if(dump_icfs_flag == insn->getBaseID())
+					dump_icfs(insn);
+			}
+
+
+
+                }
+                catch (DatabaseError_t pnide)
+                {
+                        cerr << programName << ": Unexpected database error: " << pnide << "file url: " << this_file->getURL() << endl;
+                }
+                catch (...)
+                {
+                        cerr << programName << ": Unexpected error file url: " << this_file->getURL() << endl;
+                }
+        } // end file iterator
+
+        // if any integer transforms for any files succeeded, we commit
+        if (one_success)
+	{
+		cout<<"Commiting changes...\n";
+                pqxx_interface->commit();
+	}
+
+        return 0;
+}
+
diff --git a/irdb-lib/ir_builders/SConscript b/irdb-lib/ir_builders/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..fb5eba73a4c74fbaf7a37657916c11e30cb6f271
--- /dev/null
+++ b/irdb-lib/ir_builders/SConscript
@@ -0,0 +1,64 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+installed=[]
+
+if 'build_tools' not in myenv or myenv['build_tools'] is None or int(myenv['build_tools']) == 1:
+
+	cpppath=''' 
+		 $IRDB_SDK/include 
+		 $SECURITY_TRANSFORMS_HOME/libEXEIO/include 
+		 $SECURITY_TRANSFORMS_HOME/libehp/include 
+		 $SECURITY_TRANSFORMS_HOME/libMEDSannotation/include/
+		 $SECURITY_TRANSFORMS_HOME/third_party/elfio-code
+		'''
+
+	LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+	LIBS=Split( 'irdb-cfg irdb-util ' + env.subst('$BASE_IRDB_LIBS')+ " ehp irdb-transform MEDSannotation EXEIO")
+
+	myenv=myenv.Clone(CPPPATH=Split(cpppath))
+
+	myenv.Append(CCFLAGS=" -std=c++11 -Wall")
+
+	ehframe=myenv.SharedObject("read_ehframe.cpp");
+	split_eh_frame=myenv.SharedObject("split_eh_frame.cpp");
+
+	pgm=myenv.SharedLibrary("fill_in_indtargs.so",  ehframe+split_eh_frame+Split("fill_in_indtargs.cpp check_thunks.cpp"), LIBPATH=LIBPATH, LIBS=LIBS)
+	install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install", pgm)
+	Default(install)
+	installed=installed+install
+
+	pgm=myenv.SharedLibrary("fill_in_cfg.so",  Split("fill_in_cfg.cpp")+split_eh_frame, LIBPATH=LIBPATH, LIBS=LIBS)
+	install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install", pgm)
+	Default(install)
+	installed=installed+install
+
+	pgm=myenv.SharedLibrary("fix_calls.so",  ehframe+Split("fix_calls.cpp"), LIBPATH=LIBPATH, LIBS=LIBS)
+	install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install", pgm)
+	Default(install)
+	installed=installed+install
+
+	# most programs go to $sectrans/bin
+	pgms='''clone 
+		'''
+	for i in Split(pgms):
+		# print "Registering pgm: "+ i
+		pgm=myenv.Program(target=i+".exe",  source=Split(i+".cpp"), LIBPATH=LIBPATH, LIBS=LIBS)
+		install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install/", pgm)
+		Default(install)
+		installed=installed+install
+
+
+	# ilr goes to $sectrans/plugins_install
+	# pgm=myenv.Program(target="ilr.exe",  source=Split("ilr.cpp"), LIBPATH=LIBPATH, LIBS=LIBS)
+	# install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install/", pgm)
+	# Default(install)
+	# installed=installed+install
+
+Return('installed')
+
diff --git a/irdb-lib/ir_builders/SConstruct b/irdb-lib/ir_builders/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b5b7b78c5f88640c7e8877a9df76dc9191af7498
--- /dev/null
+++ b/irdb-lib/ir_builders/SConstruct
@@ -0,0 +1,8 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return('lib')
diff --git a/irdb-lib/ir_builders/build_callgraph.cpp b/irdb-lib/ir_builders/build_callgraph.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a0ca36f7209ae516387bcc5893e81674ac06714b
--- /dev/null
+++ b/irdb-lib/ir_builders/build_callgraph.cpp
@@ -0,0 +1,104 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <irdb=-sdk>
+#include <irdb-cfg>
+#include <utils.hpp> // to_string function from libIRDB
+#include <iostream>
+#include <fstream>
+#include <stdlib.h>
+#include <string.h>
+#include <assert.h>
+
+using namespace std;
+
+//
+// main routine to build and print a call graph.
+//
+main(int argc, char* argv[])
+{
+	if(argc!=2)
+	{
+		cerr<<"Usage: "<<argv[0]<<" <variant id> "<<endl;
+		exit(-1);
+	}
+
+	string filename;
+	ostream *fout;
+	fout=&cout;
+
+
+	VariantID_t *varidp=NULL;
+	FileIR_t *firp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	try 
+	{
+
+		cerr<<"Looking up variant "<<string(argv[1])<<" from database." << endl;
+		varidp=new VariantID_t(atoi(argv[1]));
+
+		// A callgraph 
+		auto cg=Callgraph_t::factory();
+
+		assert(varidp->IsRegistered()==true);
+
+
+                for(set<File_t*>::iterator it=varidp->GetFiles().begin();
+                        it!=varidp->GetFiles().end();
+                        ++it
+                    )
+                {
+                        File_t* this_file=*it;
+                        assert(this_file);
+			cerr<<"Reading variant "<<string(argv[1])<<":"<<this_file->GetURL()
+			   <<" from database." << endl;
+
+			// read the db  
+			firp=new FileIR_t(*varidp,this_file);
+	
+			// ILR only for the main file.
+			cg->AddFile(firp);
+		}
+
+		cg->Dump(*fout);
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cerr<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cerr<<"Done!"<<endl;
+
+	if(fout!=&cout)
+		((ofstream*)fout)->close();
+		
+
+	delete varidp;
+}
+
+
diff --git a/irdb-lib/ir_builders/build_preds.cpp b/irdb-lib/ir_builders/build_preds.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ae87ac7dc1639cc39f7afb84fafcd993e0ab2c82
--- /dev/null
+++ b/irdb-lib/ir_builders/build_preds.cpp
@@ -0,0 +1,106 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <libIRDB-util.hpp>
+#include <utils.hpp> // to_string function from libIRDB
+#include <iostream>
+#include <fstream>
+#include <stdlib.h>
+#include <string.h>
+#include <assert.h>
+
+using namespace libIRDB;
+using namespace std;
+
+//
+// main routine to build and print a call graph.
+//
+int main(int argc, char* argv[])
+{
+	if(argc!=2)
+	{
+		cerr<<"Usage: "<<argv[0]<<" <variant id> "<<endl;
+		exit(-1);
+	}
+
+	string filename;
+	ostream *fout;
+	fout=&cout;
+
+
+	VariantID_t *varidp=NULL;
+	FileIR_t *firp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	try 
+	{
+
+		cerr<<"Looking up variant "<<string(argv[1])<<" from database." << endl;
+		varidp=new VariantID_t(atoi(argv[1]));
+
+		// A callgraph 
+		InstructionPredecessors_t *ip=new InstructionPredecessors_t;
+
+		assert(varidp->IsRegistered()==true);
+
+
+                for(set<File_t*>::iterator it=varidp->GetFiles().begin();
+                        it!=varidp->GetFiles().end();
+                        ++it
+                    )
+                {
+                        File_t* this_file=*it;
+                        assert(this_file);
+			cerr<<"Reading variant "<<string(argv[1])<<":"<<this_file->GetURL()
+			   <<" from database." << endl;
+
+			// read the db  
+			firp=new FileIR_t(*varidp,this_file);
+	
+			// ILR only for the main file.
+			ip->AddFile(firp);
+		}
+
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cerr<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cerr<<"Done!"<<endl;
+
+	if(fout!=&cout)
+		((ofstream*)fout)->close();
+		
+
+	delete varidp;
+
+	return 0;
+}
+
+
diff --git a/irdb-lib/ir_builders/calc_conflicts.cpp b/irdb-lib/ir_builders/calc_conflicts.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..15dd95ead800f405a927cc48f0c4347cb866f821
--- /dev/null
+++ b/irdb-lib/ir_builders/calc_conflicts.cpp
@@ -0,0 +1,201 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+#include <string.h>
+#include <map>
+#include <assert.h>
+#include <elf.h>
+#include <sys/mman.h>
+#include <ctype.h>
+#include "targ-config.h"
+#include "elfio/elfio.hpp"
+#include "elfio/elfio_dump.hpp"
+
+
+
+
+int odd_target_count=0;
+int bad_target_count=0;
+int bad_fallthrough_count=0;
+
+using namespace libIRDB;
+using namespace std;
+
+set< pair<DatabaseID_t,int> > missed_instructions;
+int failed_target_count=0;
+
+pqxxDB_t pqxx_interface;
+
+long long num_addresses=0,num_conflicts=0,tot_conflicts=0;
+long long total_bytes=0;
+
+void count_conflicts (FileIR_t* virp)
+{
+	map<int,int> conflict_map;
+
+
+	/* for each instruction in the IR */
+	for(
+		set<Instruction_t*>::const_iterator it=virp->GetInstructions().begin();
+		it!=virp->GetInstructions().end(); 
+		++it
+	   )
+	{
+		Instruction_t *insn=*it;
+
+		VirtualOffset_t vo=insn->GetAddress()->GetVirtualOffset();
+
+		for(int i=0;i<insn->GetDataBits().length();i++)
+			conflict_map[(vo+i)]++;
+	}
+
+
+	for(map<int,int>::const_iterator it=conflict_map.begin();
+		it!=conflict_map.end();
+		++it)
+	{
+		int address=(*it).first;
+		int conflicts=(*it).second;
+
+		num_addresses++;
+		if(conflicts>1)
+		{
+			num_conflicts++;
+			tot_conflicts+=conflicts;
+		}
+			
+
+
+	}
+
+}
+
+
+
+
+void get_total(char* filename)
+{
+
+	FILE* loa=fopen(filename, "r");
+	
+	assert(loa && "Cannot open input file");
+		
+
+       	IRDB_Elf_Off sec_hdr_off, sec_off;
+       	IRDB_Elf_Half secnum, strndx, secndx;
+       	IRDB_Elf_Word secsize;
+	
+
+       	/* allcoate memory  */
+       	IRDB_Elf_Ehdr elfhdr;
+
+       	/* Read ELF header */
+       	fread((char*)&elfhdr, sizeof(IRDB_Elf_Ehdr), 1, loa);
+
+       	sec_hdr_off = elfhdr.e_shoff;
+       	secnum = elfhdr.e_shnum;
+       	strndx = elfhdr.e_shstrndx;
+
+       	/* Read Section headers */
+       	IRDB_Elf_Shdr *sechdrs=(IRDB_Elf_Shdr*)malloc(sizeof(IRDB_Elf_Shdr)*secnum);
+       	fseek(loa,sec_hdr_off, std::ios_base::beg);
+       	fread((char*)sechdrs, sizeof(IRDB_Elf_Shdr), secnum, loa);
+
+
+	
+       	/* look through each section and find the missing target*/
+       	for (secndx=1; secndx<secnum; secndx++)
+	{
+       		int flags = sechdrs[secndx].sh_flags;
+
+       		/* not a loaded section */
+       		if( (flags & SHF_ALLOC) != SHF_ALLOC)
+               		continue;
+		
+       		/* loaded, and contains instruction, record the bounds */
+       		if( (flags & SHF_EXECINSTR) != SHF_EXECINSTR)
+               		continue;
+
+
+        	total_bytes+=sechdrs[secndx].sh_size;
+	}
+
+
+}
+
+
+
+main(int argc, char* argv[])
+{
+
+	if(argc!=3)
+	{
+		cerr<<"Usage: calc_conflicts <id> <a.out>"<<endl;
+		exit(-1);
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t * virp=NULL;
+
+	try 
+	{
+		/* setup the interface to the sql server */
+		BaseObj_t::SetInterface(&pqxx_interface);
+
+		pidp=new VariantID_t(atoi(argv[1]));
+
+		assert(pidp->IsRegistered()==true);
+
+		cout<<"New Variant, after reading registration, is: "<<*pidp << endl;
+
+		// read the db  
+		virp=new FileIR_t(*pidp);
+
+		get_total(argv[2]);
+		count_conflicts(virp);
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	assert(virp && pidp);
+
+	cout<<"# ATTRIBUTE calc_conflicts::num_addresses="<<std::dec<<num_addresses<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::num_conflicts="<<std::dec<<num_conflicts<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::total_conflicts="<<std::dec<<tot_conflicts<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::pct_conflicts="<<std::fixed<<((float)num_conflicts/(float)tot_conflicts)*100.00<<"%"<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::ave_conflicts="<<std::dec<<((double)tot_conflicts/num_addresses)<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::ave_bytes_conflicted="<<std::dec<<((double)num_conflicts/num_addresses)<<endl;
+	cout <<"# ATTRIBUTE calc_conflicts::total_executable_bytes = "<< std::dec << total_bytes<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::ave_conflicts_within_exe="<<std::dec<<((double)tot_conflicts/total_bytes)<<endl;
+	cout<<"# ATTRIBUTE calc_conflicts::ave_bytes_conflicted_within_exe="<<std::dec<<((double)num_conflicts/total_bytes)<<endl;
+
+
+	delete virp;
+	delete pidp;
+}
diff --git a/irdb-lib/ir_builders/check_thunks.cpp b/irdb-lib/ir_builders/check_thunks.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..716b2cd30cebaa0a6a9b49a4fe26b883aa426c44
--- /dev/null
+++ b/irdb-lib/ir_builders/check_thunks.cpp
@@ -0,0 +1,413 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+
+
+
+#include <irdb-core>
+#include <algorithm>
+#include <iostream>
+#include <stdlib.h>
+#include <assert.h>
+#include <string.h>
+#include <elf.h>
+
+#include "check_thunks.hpp"
+#include "fill_in_indtargs.hpp"
+
+
+using namespace IRDB_SDK;
+using namespace std;
+
+#define HIWORD(a) ((a)&0xFFFF0000)
+
+
+/*
+ * check_for_thunk_offsets - check non-function thunks for extra offsets 
+ */
+void check_for_thunk_offsets(FileIR_t* firp, VirtualOffset_t thunk_base)
+{
+
+	for(auto insn : firp->getInstructions())
+	{
+		const auto d=DecodedInstruction_t::factory(insn);
+		if(d->getMnemonic()=="add")
+		{
+			// check that arg2 is a constant
+			if(!d->getOperand(1)->isConstant())
+				continue;
+
+			auto addoff=d->getOperand(1)->getConstant(); 
+
+			/* bounds check gently */
+			if(0<addoff && addoff<100)
+				continue;
+
+			possible_target(thunk_base+addoff, 0, ibt_provenance_t::ibtp_text);
+		}
+		// else if(string(d.Instruction.Mnemonic)==string("lea "))
+		if(d->getMnemonic()=="lea")
+		{
+			assert (d->getOperand(1)->isMemory());
+
+			/* no indexing please! */
+			if(d->getOperand(1)->hasIndexRegister())
+				continue;
+
+			auto leaoff=d->getOperand(1)->getMemoryDisplacement();
+
+			/* bounds check gently */
+			if(0<leaoff && leaoff<100)
+				continue;
+			
+			/* record that there's a possible target here */
+			possible_target(thunk_base+leaoff, 0, ibt_provenance_t::ibtp_text);
+			
+		}
+			
+	}
+}
+
+void check_for_thunk_offsets(FileIR_t* firp, Instruction_t *thunk_insn, string reg, uint64_t offset)
+{
+
+	auto thunk_base=thunk_insn->getFallthrough()->getAddress()->getVirtualOffset()+offset;
+
+	/* don't check inserted thunk addresses */
+	if(thunk_insn->getAddress()->getVirtualOffset()==0)
+		return;
+
+	check_for_thunk_offsets(firp,thunk_base);
+}
+
+
+
+/*
+ * check_func_for_thunk_offsets - we know that insn represents a thunk call, with reg+offset as the constant.
+ * check the rest of the function for offsets that might help form a code pointer.
+ */
+void check_func_for_thunk_offsets(Function_t *func, Instruction_t* thunk_insn,
+	string reg, uint64_t offset)
+{
+
+
+
+	auto thunk_base=thunk_insn->getFallthrough()->getAddress()->getVirtualOffset()+offset;
+
+
+	/* don't check inserted thunk addresses */
+	if(thunk_insn->getAddress()->getVirtualOffset()==0)
+		return;
+
+	for(auto insn : func->getInstructions())
+	{
+		// if it has a targ and fallthrough (quick test) it might be a call 
+		const auto d=DecodedInstruction_t::factory(insn);
+	
+		if(d->getMnemonic()=="add")
+		{
+			// check that arg2 is a constant
+			if(!d->getOperand(1)->isConstant())
+				continue;
+
+			auto addoff=d->getOperand(1)->getConstant(); 
+
+			/* bounds check gently */
+			if(0<addoff && addoff<100)
+				continue;
+
+			/* record that there's a possible target here */
+// 			cout <<"Possible thunk target (add): call:"<<thunk_call_addr<<" offset:"<<thunk_call_offset
+//			     <<" addoff: " << addoff << " total: "<< (thunk_base+addoff)<<endl;
+			possible_target(thunk_base+addoff, 0, ibt_provenance_t::ibtp_text);
+		}
+		else if(d->getMnemonic()=="lea")
+		{
+			assert (d->getOperand(1)->isMemory()); 
+
+			/* no indexing please! */
+			if(!d->getOperand(1)->hasIndexRegister())
+				continue;
+
+			VirtualOffset_t leaoff=d->getOperand(1)->getMemoryDisplacement();
+
+			/* bounds check gently */
+			if(0<leaoff && leaoff<100)
+				continue;
+			
+			/* record that there's a possible target here */
+// 			cout <<"Possible thunk target (lea): call:"<<thunk_call_addr<<" offset:"<<thunk_call_offset
+// 			     <<" leaoff: " << leaoff << " total: "<< (thunk_base+leaoff)<<endl;
+			possible_target(thunk_base+leaoff, 0, ibt_provenance_t::ibtp_text);
+			
+		}
+			
+	}
+}
+
+
+/*
+ * is_thunk_load - look for a mov reg<[esp], return reg in output parameter.
+ */
+bool is_thunk_load(Instruction_t* insn, string &reg)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+	if(d->getMnemonic()!="mov")
+		return false;
+
+	if(!d->getOperand(1)->isMemory() || d->getOperand(1)->getString()!="esp")
+		return false;
+
+	reg=d->getOperand(0)->getString();
+	return true;
+}
+
+/*
+ * is_ret - return true if insn is a return 
+ */
+bool is_ret(Instruction_t* insn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+	return d->isReturn(); 
+}
+
+/*
+ * is_pop - return true if insn is a return
+ */
+bool is_pop(Instruction_t* insn, string &reg)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+        if(d->getMnemonic()!="pop")
+                return false;
+
+	reg=d->getOperand(0)->getString();
+        return true;
+}
+
+
+
+/* 
+ * is_thunk_call - check if this instruction is a call to a thunk function, return the thunk function's reg.
+ */
+/* note: reg is output paramater */
+bool is_thunk_call(Instruction_t* insn, string &reg)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+	/* not a call */
+	if(!d->isCall())
+		return false;
+
+	/* no target in IRDB */
+	if(insn->getTarget()==NULL)
+		return false;
+
+	/* Target not the right type of load */
+	if(!is_thunk_load(insn->getTarget(),reg))
+		return false;
+
+	/* target has no FT? */
+	if(!insn->getTarget()->getFallthrough())
+		return false;
+
+	/* target's FT is a return insn */
+	if(!is_ret(insn->getTarget()->getFallthrough()))
+		return false;
+
+	return true;
+}
+
+bool is_thunk_call_type2(Instruction_t* insn, string &reg, Instruction_t** newinsn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+	/* not a call */
+	if(!d->isCall())
+		return false;
+
+	/* no target in IRDB */
+	if(insn->getTarget()==NULL)
+		return false;
+
+	if(insn->getTarget() != insn->getFallthrough())
+		return false;
+
+	/* target's FT is a return insn */
+	if(!is_pop(insn->getTarget(), reg))
+		return false;
+
+	*newinsn=insn->getTarget()->getFallthrough();
+
+	return true;
+}
+
+/* 
+ * is_thunk_add - Check the given instruction for an add of reg, return the constant K1 
+ */
+/* note: offset is an output parameter */
+bool is_thunk_add(Instruction_t *insn, string reg, uint64_t &offset)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+	// make sure it's an add instruction 
+	if(d->getMnemonic()!="add")
+		return false;
+
+	// check that it's an add of the proper reg
+	if(d->getOperand(0)->getString()!=reg)
+		return false;
+
+	// check that arg2 is a constant
+	if(!d->getOperand(1)->isConstant())
+		return false;
+
+	offset=d->getOperand(1)->getConstant();
+
+	auto intoff=d->getOperand(1)->getConstant(); 
+
+	/* bounds check gently */
+	if(0<intoff && intoff<100)
+		return false;
+
+	return true;
+}
+
+/* 
+ * check_func_for_thunk_calls - check this function for a thunk call (see check_for_thunks for description of thunk calls)
+ */
+void check_func_for_thunk_calls(Function_t* func)
+{
+	// for each insn in the func 
+	for(auto insn : func->getInstructions())
+	{
+		// if it has a targ and fallthrough (quick test) it might be a call 
+		/* check if we might be calling a thunk */
+		if(insn->getFallthrough() && insn->getTarget())
+		{
+
+			// check for a call, followed by an add of reg (note the output params of reg and offset)
+			string reg;
+			uint64_t offset=0;
+			if(is_thunk_call(insn,reg) && 
+				is_thunk_add(insn->getFallthrough(),reg,offset))
+			{
+				check_func_for_thunk_offsets(func,insn,reg,offset);
+			}
+		}
+	}
+}
+
+
+
+void check_non_funcs_for_thunks(FileIR_t *firp)
+{
+	// for each insn in the func 
+	for(auto insn :  firp->getInstructions())
+	{
+		// if it has a targ and fallthrough (quick test) it might be a call 
+
+		/* these instructions/thunks are checked with the functions */
+
+		/* check if we might be calling a thunk */
+		if(insn->getFallthrough() && insn->getTarget())
+		{
+
+			// check for a call, followed by an add of reg (note the output params of reg and offset)
+			string reg; 
+			uint64_t offset=0;
+			if(is_thunk_call(insn,reg) && 
+				is_thunk_add(insn->getFallthrough(),reg,offset))
+			{
+				cout<<"Found non-function thunk at "<<	
+					insn->getAddress()->getVirtualOffset()<<endl;
+				check_for_thunk_offsets(firp,insn,reg,offset);
+			}
+		}
+	}
+}
+
+
+/* 
+ * check_for_thunks - 
+ * 
+ * check the program (file) for this pattern:
+ * 
+ *	 		call   ebx_thunk
+ *  	L1:		add    K1,%ebx
+ *
+ * 	ebx_thunk:	mov ebx <- [esp]
+ * 			ret
+ * 
+ *  If found, check the function for L1+K1+K2 (where K2 is any constant in the function)
+ *  If L1+k1+k2 is found, and points at a code address (outside this function?), mark it as an indirect branch target.
+ * 
+ */
+void check_for_thunks(FileIR_t* firp, const std::set<VirtualOffset_t>&  thunk_bases)
+{
+	/* thunk bases is the module start's found for this firp */
+
+	cout<<"Starting check for thunks"<<endl;
+
+	for(auto offset : thunk_bases)
+		check_for_thunk_offsets(firp,offset);
+}
+
+void find_all_module_starts(FileIR_t* firp, set<VirtualOffset_t> &thunk_bases)
+{
+	thunk_bases.clear();
+
+	cout<<"Finding thunk bases"<<endl;
+
+	// for each insn in the func 
+	for(auto insn : firp->getInstructions())
+	{
+		// if it has a targ and fallthrough (quick test) it might be a call 
+		/* check if we might be calling a thunk */
+		if(insn->getFallthrough() && insn->getTarget())
+		{
+			// check for a call, followed by an add of reg (note the output params of reg and offset)
+			string reg; 
+			uint64_t offset=0;
+			if(is_thunk_call(insn,reg) && 
+				is_thunk_add(insn->getFallthrough(),reg,offset))
+			{
+				auto thunk_base=insn->getFallthrough()->getAddress()->getVirtualOffset()+ offset;
+				if(thunk_bases.find(thunk_base)==thunk_bases.end())
+					cout<<"Found new thunk at "<<insn->getAddress()->getVirtualOffset()<<" with base: "<<hex<<thunk_base<<endl;
+				thunk_bases.insert(thunk_base);
+			}
+			Instruction_t* newinsn=NULL;
+			if(is_thunk_call_type2(insn,reg,&newinsn))
+			{
+				if(newinsn && is_thunk_add(newinsn,reg,offset))
+				{
+					VirtualOffset_t thunk_base=insn->getFallthrough()->getAddress()->getVirtualOffset()+ offset;
+					if(thunk_bases.find(thunk_base)==thunk_bases.end())
+						cout<<"Found new thunk at "<<insn->getAddress()->getVirtualOffset()<<" with base: "<<hex<<thunk_base<<endl;
+					thunk_bases.insert(thunk_base);
+				}
+			}
+		}
+	}
+}
diff --git a/irdb-lib/ir_builders/check_thunks.hpp b/irdb-lib/ir_builders/check_thunks.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..27b77593fce91e937501b16524d81cc9323e753b
--- /dev/null
+++ b/irdb-lib/ir_builders/check_thunks.hpp
@@ -0,0 +1,33 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#ifndef check_thunks_hpp
+#define check_thunks_hpp
+
+#include <set>
+#include <irdb-core>
+
+void find_all_module_starts(IRDB_SDK::FileIR_t* firp, std::set<IRDB_SDK::VirtualOffset_t>& thunk_bases);
+void check_for_thunks(IRDB_SDK::FileIR_t* firp, const std::set<IRDB_SDK::VirtualOffset_t>& thunk_bases);
+
+
+#endif
+
diff --git a/irdb-lib/ir_builders/clone.cpp b/irdb-lib/ir_builders/clone.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d5211b72361faafdeb6d11acc4b5300f103f725e
--- /dev/null
+++ b/irdb-lib/ir_builders/clone.cpp
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <irdb-core>
+#include <iostream>
+#include <fstream>
+
+#include <stdlib.h>
+
+using namespace IRDB_SDK;
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=3)
+	{
+		cerr<<"Usage: clone <vid> <output.id>"<<endl;
+		exit(-1);
+	}
+
+
+	/* setup the interface to the sql server */
+	auto pqxx_interface=pqxxDB_t::factory();
+	BaseObj_t::setInterface(pqxx_interface.get());
+
+
+	try 
+	{
+		auto pidp=VariantID_t::factory(atoi(argv[1]));
+		assert(pidp->isRegistered()==true);
+
+		auto newpidp=pidp->clone();
+		assert(newpidp->isRegistered()==true);
+
+		cout<<"Cloned Variant is: "<<*newpidp << endl;
+
+		// commit the changes to the db if all went well 
+		pqxx_interface->commit();
+
+		auto  newpid_id=newpidp->getBaseID();
+		ofstream f;
+		f.open(argv[2]);
+		if(!f.is_open())
+		{
+			cerr<<"Cannot open output file"<<endl;
+			exit(-1);
+		}
+		f<<std::dec<<newpid_id<<endl;
+		f.close();
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+
+
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/create_variant.cpp b/irdb-lib/ir_builders/create_variant.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..98052436e34a3ced2ec237ff235d83117017525e
--- /dev/null
+++ b/irdb-lib/ir_builders/create_variant.cpp
@@ -0,0 +1,78 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: create_variant <name>"<<endl;
+		exit(-1);
+	}
+
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+
+	VariantID_t *pidp=NULL;
+	try 
+	{
+		pidp=new VariantID_t();
+
+		assert(pidp->IsRegistered()==false);
+
+		pidp->SetName(argv[1]);
+
+		cout<<"New Variant, before registration, is: "<<*pidp << endl;
+
+		pidp->Register();
+
+		assert(pidp->IsRegistered()==true);
+
+		cout<<"New Variant, after registration, is: "<<*pidp << endl;
+
+		pidp->WriteToDB();
+
+		cout<<"New Variant, after writing to DB, is: "<<*pidp << endl;
+
+		// commit the changes to the db if all went well 
+		pqxx_interface.Commit();
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	delete pidp;
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/create_variantir.cpp b/irdb-lib/ir_builders/create_variantir.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..8a8efe54b05d3df3f3371c68ee9339962ff76b8b
--- /dev/null
+++ b/irdb-lib/ir_builders/create_variantir.cpp
@@ -0,0 +1,84 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: create_variant <name>"<<endl;
+		exit(-1);
+	}
+
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+
+	VariantID_t *pidp=NULL;
+	FileIR_t * virp=NULL;
+	try 
+	{
+		pidp=new VariantID_t();
+
+		assert(pidp->IsRegistered()==false);
+
+		pidp->SetName(argv[1]);
+
+		cout<<"New Variant, before registration, is: "<<*pidp << endl;
+
+		pidp->Register();
+
+		assert(pidp->IsRegistered()==true);
+
+		cout<<"New Variant, after registration, is: "<<*pidp << endl;
+
+		pidp->WriteToDB();
+
+		cout<<"New Variant, after writing to DB, is: "<<*pidp << endl;
+
+		virp=new FileIR_t(*pidp);
+
+
+		// commit the changes to the db if all went well 
+		pqxx_interface.Commit();
+
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	delete virp;
+	delete pidp;
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/decode_test.cpp b/irdb-lib/ir_builders/decode_test.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..cec74d350f6be02170266507e85b1bfe93caabd6
--- /dev/null
+++ b/irdb-lib/ir_builders/decode_test.cpp
@@ -0,0 +1,16 @@
+#include <libIRDB-core.hpp>
+
+using namespace std;
+using namespace libIRDB;
+
+int main()
+{
+
+	FileIR_t::SetArchitecture(64,admtX86_64);
+
+	for(auto i=0U; i<10*1000*1000; i++)
+	{
+		const auto d=DecodedInstruction_t(1024, "\x90", 1);
+	}
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/drop_variant.cpp b/irdb-lib/ir_builders/drop_variant.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..14d0dd98d82b1047518294129c23de896c1d7dd8
--- /dev/null
+++ b/irdb-lib/ir_builders/drop_variant.cpp
@@ -0,0 +1,70 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: simple (<pid>)"<<endl;
+		exit(-1);
+	}
+
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+
+	VariantID_t *pidp=NULL;
+	try 
+	{
+		pidp=new VariantID_t(atoi(argv[1]));
+		cout<<"Variant "<< argv[1]<< " found in db: "<<*pidp << ".  Dropping..."<< endl;
+		pidp->DropFromDB();
+		pqxx_interface.Commit();	
+	}
+	catch (DatabaseError_t pnide)
+	{
+		if(pnide.GetErrorCode()==DatabaseError_t::VariantNotInDatabase)
+		{
+			cout<<"Variant "<< argv[1]<< " not found in db"<<endl;
+			exit(-2);
+		}
+       		else
+		{
+			cout<<"Unexpected database error: "<<pnide<<endl;
+			exit(-1);
+		}
+        }
+
+	cout<<"Done!"<<endl;
+	delete pidp;
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/fill_in_cfg.cpp b/irdb-lib/ir_builders/fill_in_cfg.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..85ce8cf0efda608519158b4c4e1e42f67b89354b
--- /dev/null
+++ b/irdb-lib/ir_builders/fill_in_cfg.cpp
@@ -0,0 +1,732 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include "fill_in_cfg.hpp"
+#include <iostream>
+#include <fstream>
+#include <string.h>
+#include <assert.h>
+#include <sys/mman.h>
+#include <ctype.h>
+#include "elfio/elfio.hpp"
+#include "split_eh_frame.hpp"
+
+using namespace std;
+using namespace EXEIO;
+using namespace IRDB_SDK;
+
+void PopulateCFG::populate_instruction_map
+	(
+		map< pair<DatabaseID_t,VirtualOffset_t>, Instruction_t*> &insnMap,
+		FileIR_t *firp
+	)
+{
+	/* start from scratch each time */
+	insnMap.clear();
+
+
+	/* for each instruction in the IR */
+	for(auto insn : firp->getInstructions())
+	{
+		auto fileID=insn->getAddress()->getFileID();
+		auto vo=insn->getAddress()->getVirtualOffset();
+
+		auto p=pair<DatabaseID_t,VirtualOffset_t>(fileID,vo);
+
+		assert(insnMap[p]==NULL);
+		insnMap[p]=insn;
+	}
+
+}
+
+void PopulateCFG::set_fallthrough
+	(
+	map< pair<DatabaseID_t,VirtualOffset_t>, Instruction_t*> &insnMap,
+	DecodedInstruction_t *disasm, Instruction_t *insn, FileIR_t *firp
+	)
+{
+	assert(disasm);
+	assert(insn);
+
+	if(insn->getFallthrough())
+		return;
+	
+	// check for branches with targets 
+	if(
+		(disasm->isUnconditionalBranch() ) ||	// it is a unconditional branch 
+		(disasm->isReturn())			// or a return
+	  )
+	{
+		// this is a branch with no fallthrough instruction
+		return;
+	}
+
+	/* get the address of the next instrution */
+	
+	auto virtual_offset=insn->getAddress()->getVirtualOffset() + insn->getDataBits().size();
+
+	/* create a pair of offset/file */
+	auto p=pair<DatabaseID_t,VirtualOffset_t>(insn->getAddress()->getFileID(),virtual_offset);
+	
+	/* lookup the target insn from the map */
+	auto fallthrough_insn=insnMap[p];
+
+	/* sanity, note we may see odd control transfers to 0x0 */
+	if(fallthrough_insn==NULL &&   virtual_offset!=0)
+	{
+		cout<<"Cannot set fallthrough for "<<std::hex<<insn->getAddress()->getVirtualOffset();
+		cout<< " : "<<insn->getDisassembly()<<endl;
+		bad_fallthrough_count++;
+	}
+
+	/* set the target for this insn */
+	if(fallthrough_insn!=0)
+	{
+		fallthroughs_set++;
+		insn->setFallthrough(fallthrough_insn);
+	}
+	else
+		missed_instructions.insert(pair<DatabaseID_t,VirtualOffset_t>(insn->getAddress()->getFileID(),virtual_offset));
+}
+
+
+void PopulateCFG::set_target
+	(
+	map< pair<DatabaseID_t,VirtualOffset_t>, Instruction_t*> &insnMap,
+	DecodedInstruction_t *disasm, Instruction_t *insn, FileIR_t *firp
+	)
+{
+
+	assert(insn);
+	assert(disasm);
+
+	if(insn->getTarget())
+		return;
+
+	const auto &operands = disasm->getOperands();
+	for(auto operand : operands)
+	{	
+		// check for branches with targets 
+		if(
+			disasm->isBranch() &&		// it is a branch 
+			!disasm->isReturn() && 		// and not a return
+			operand->isConstant()		// and has a constant argument 
+		  )
+		{
+	//		cout<<"Found direct jump with addr=" << insn->getAddress()->getVirtualOffset() <<
+	//			" disasm="<<disasm->CompleteInstr<<" ArgMnemonic="<<
+	//			disasm->Argument1.ArgMnemonic<<"."<<endl;
+
+			/* get the offset */
+			auto virtual_offset=disasm->getAddress();
+
+			/* create a pair of offset/file */
+			auto p=pair<DatabaseID_t,VirtualOffset_t>(insn->getAddress()->getFileID(),virtual_offset);
+		
+			/* lookup the target insn from the map */
+			auto target_insn=insnMap[p];
+
+			/* sanity, note we may see odd control transfers to 0x0 */
+			if(target_insn==NULL)
+			{
+				unsigned char first_byte=0;
+				if(insn->getFallthrough())
+					first_byte=(insn->getFallthrough()->getDataBits().c_str())[0];
+				VirtualOffset_t jump_dist=virtual_offset-(insn->getAddress()->getVirtualOffset()+(insn->getDataBits()).size());
+				if(	
+					// jump 1 byte forward
+					jump_dist == 1 &&
+
+					// and we calculated the fallthrough
+					insn->getFallthrough()!=NULL &&
+
+					// and the fallthrough starts with a lock prefix
+					first_byte==0xf0
+				  )
+				{
+					odd_target_count++;
+					target_insn=insn->getFallthrough();
+				}
+				else
+				{
+					if(virtual_offset!=0)
+						cout<<"Cannot set target (target="<< std::hex << virtual_offset << ") for "<<std::hex<<insn->getAddress()->getVirtualOffset()<<"."<<endl;
+					bad_target_count++;
+				}
+			}
+
+			/* set the target for this insn */
+			if(target_insn!=0)
+			{
+				targets_set++;
+				insn->setTarget(target_insn);
+			}
+			else
+				missed_instructions.insert( pair<DatabaseID_t,VirtualOffset_t>(insn->getAddress()->getFileID(),virtual_offset));
+
+		}
+	}
+}
+
+File_t* PopulateCFG::find_file(FileIR_t* firp, DatabaseID_t fileid)
+{
+	assert(firp->getFile()->getBaseID()==fileid);
+	return firp->getFile();
+}
+
+
+void PopulateCFG::add_new_instructions(FileIR_t *firp)
+{
+	int found_instructions=0;
+	for(auto p : missed_instructions)
+	{
+		/* get the address we've missed */
+		auto missed_address=p.second;
+
+		/* get the address ID of the instruction that's missing the missed addressed */
+		auto missed_fileid=p.first;
+		
+		/* figure out which file we're looking at */
+		auto filep=find_file(firp,missed_fileid);
+		assert(filep);
+
+
+
+        	int secnum = elfiop->sections.size(); 
+		int secndx=0;
+
+		bool found=false;
+	
+        	/* look through each section and find the missing target*/
+        	for (secndx=1; secndx<secnum; secndx++)
+		{
+        		/* not a loaded section */
+        		if( !elfiop->sections[secndx]->isLoadable()) 
+                		continue;
+		
+        		/* loaded, and contains instruction, record the bounds */
+        		if( !elfiop->sections[secndx]->isExecutable()) 
+                		continue;
+		
+        		VirtualOffset_t first=elfiop->sections[secndx]->get_address();
+        		VirtualOffset_t second=elfiop->sections[secndx]->get_address()+elfiop->sections[secndx]->get_size();
+
+			/* is the missed instruction in this section */
+			if(first<=missed_address && missed_address<second)
+			{
+				const char* data=elfiop->sections[secndx]->get_data();
+				// second=data?
+				VirtualOffset_t offset_into_section=missed_address-elfiop->sections[secndx]->get_address();
+	
+				/* disassemble the instruction */
+				auto disasm_p=DecodedInstruction_t::factory(missed_address, (void*)&data[offset_into_section], elfiop->sections[secndx]->get_size()-offset_into_section );
+				auto &disasm=*disasm_p;
+
+
+
+				/* if we found the instruction, but can't disassemble it, then we skip out for now */
+				if(!disasm.valid()) 
+				{
+					if(getenv("VERBOSE_CFG"))
+						cout<<"Found invalid insn at "<<missed_address<<endl;
+					break;
+				}
+				else if(getenv("VERBOSE_CFG"))
+					cout<<"Found valid insn at "<<missed_address<<": "<<disasm.getDisassembly()<<endl;
+
+                		const auto instr_len = disasm.length();
+
+				/* intel instructions have a max size of 16 */
+				assert(1<=instr_len && instr_len<=16);
+
+
+				/* here we are certain we found the instruction  */
+				found=true;
+
+				/* get the new bits for an instruction */
+				string newinsnbits;
+				newinsnbits.resize(instr_len);
+				for(auto i=0U;i<instr_len;i++)
+					newinsnbits[i]=data[offset_into_section+i];
+
+				/* create a new address */
+				/*
+				auto newaddr=new AddressID_t();
+				assert(newaddr);
+				newaddr->setVirtualOffset(missed_address);
+				newaddr->setFileID(missed_fileid);
+				firp->getAddresses().insert(newaddr);
+				*/
+				auto newaddr=firp->addNewAddress(missed_fileid,missed_address);
+
+				/* create a new instruction */
+				/*
+				auto newinsn=new Instruction_t();
+				assert(newinsn);
+				newinsn->setAddress(newaddr);
+				newinsn->setDataBits(newinsnbits);
+				newinsn->setComment(disasm.getDisassembly()+string(" from fill_in_cfg "));
+				firp->getInstructions().insert(newinsn);
+				newinsn->setAddress(newaddr);
+				*/
+				auto newinsn=firp->addNewInstruction(newaddr, nullptr, newinsnbits, disasm.getDisassembly()+string(" from fill_in_cfg "), nullptr);
+				(void)newinsn;// just add to IR
+
+				/* fallthrough/target/is indirect will be set later */
+
+				/* insert into the IR */
+
+
+				cout<<"Found new instruction, "<<newinsn->getComment()<<", at "<<std::hex<<newinsn->getAddress()->getVirtualOffset()<<" in file "<<"<no name yet>"<<"."<<endl; 
+				found_instructions++;
+			}
+		
+		}
+		if(!found)
+		{
+			failed_target_count++;
+	
+			cout<<"Cannot find address "<<std::hex<<missed_address<<" in file "<<"<no name yet>"<<"."<<endl; 
+		} 
+	}	
+	cout<<"Found a total of "<<std::dec<<found_instructions<<" new instructions."<<endl;
+
+}
+
+void PopulateCFG::fill_in_cfg(FileIR_t *firp)
+{
+	int round=0;
+	
+	do
+	{
+		bad_target_count=0;
+		bad_fallthrough_count=0;
+		failed_target_count=0;
+		missed_instructions.clear();
+
+		map< pair<DatabaseID_t,VirtualOffset_t>, Instruction_t*> insnMap;
+		populate_instruction_map(insnMap, firp);
+
+		cout << "Found "<<firp->getInstructions().size()<<" instructions." <<endl;
+
+		/* for each instruction, disassemble it and set the target/fallthrough */
+		for(auto insn : firp->getInstructions())
+		{
+      			auto disasm=DecodedInstruction_t::factory(insn);
+	
+      			const auto instr_len = disasm->length();
+	
+			assert(instr_len==insn->getDataBits().size());
+	
+			set_fallthrough(insnMap, disasm.get(), insn, firp);
+			set_target(insnMap, disasm.get(), insn, firp);
+			
+		}
+		if(bad_target_count>0)
+			cout<<std::dec<<"Found "<<bad_target_count<<" bad targets at round "<<round<<endl;
+		if(bad_fallthrough_count>0)
+			cout<<"Found "<<bad_fallthrough_count<<" bad fallthroughs at round "<<round<<endl;
+		cout<<"Missed instruction count="<<missed_instructions.size()<<endl;
+
+		add_new_instructions(firp);
+
+		round++;
+
+	/* keep trying this while we're resolving targets.  if at any point we fail to resolve a new target/fallthrough address, then we give up */
+	} while(missed_instructions.size()>failed_target_count);
+
+	cout<<"Caution: Was unable to find instructions for these addresses:"<<hex<<endl;
+	for(auto p : missed_instructions)
+	{
+		/* get the address we've missed */
+		VirtualOffset_t missed_address=p.second;
+		cout << missed_address << ", ";
+	}
+	cout<<dec<<endl;
+
+
+	/* set the base IDs for all instructions */
+	firp->setBaseIDS();
+
+	/* for each instruction, set the original address id to be that of the address id, as fill_in_cfg is 
+	 * designed to work on only original programs.
+	 */
+	for(auto insn : firp->getInstructions())
+		insn->setOriginalAddressID(insn->getAddress()->getBaseID());
+
+
+}
+
+bool PopulateCFG::is_in_relro_segment(const int secndx)
+{
+	ELFIO::elfio *real_elfiop = reinterpret_cast<ELFIO::elfio*>(elfiop->get_elfio()); 
+	if(!real_elfiop)
+		return false;
+
+	int segnum = real_elfiop->segments.size();
+
+	VirtualOffset_t sec_start=(VirtualOffset_t)(elfiop->sections[secndx]->get_address());
+	VirtualOffset_t sec_end=(VirtualOffset_t)(elfiop->sections[secndx]->get_address() + elfiop->sections[secndx]->get_size() - 1 );
+
+	/* look through each section */
+	for (int segndx=1; segndx<segnum; segndx++)
+	{
+		ELFIO::Elf_Word type=real_elfiop->segments[segndx]->get_type();
+#ifndef PT_GNU_RELRO
+#define PT_GNU_RELRO    0x6474e552      /* Read-only after relocation */
+#endif
+
+		if(type==PT_GNU_RELRO)
+		{
+			VirtualOffset_t seg_start=(VirtualOffset_t)(real_elfiop->segments[segndx]->get_virtual_address());
+			VirtualOffset_t seg_end=(VirtualOffset_t)(real_elfiop->segments[segndx]->get_virtual_address() + real_elfiop->segments[segndx]->get_memory_size() - 1 );
+
+			// check if start lies within 
+			if(seg_start <= sec_start  && sec_start <= seg_end)
+				return true;
+
+			// check if end lies within 
+			if(seg_start <= sec_end  && sec_end <= seg_end)
+				return true;
+			
+			// check if crosses
+			if(sec_start < seg_start  && seg_end < sec_end)
+				return true;
+		}
+	}
+
+	return false;
+}
+
+void PopulateCFG::fill_in_scoops(FileIR_t *firp)
+{
+
+	auto max_base_id=firp->getMaxBaseID();
+	auto secnum = elfiop->sections.size();
+	auto secndx=0;
+
+	/* look through each section */
+	for (secndx=1; secndx<secnum; secndx++)
+	{
+		/* not a loaded section, try next section */
+		if(!elfiop->sections[secndx]->isLoadable()) 
+		{
+			cout<<"Skipping scoop for section (not loadable) "<<elfiop->sections[secndx]->get_name()<<endl;
+			continue;
+		}
+
+        	if(elfiop->sections[secndx]->isWriteable() && elfiop->sections[secndx]->isExecutable()) 
+		{
+			ofstream fout("warning.txt");
+			fout<<"Found that section "<<elfiop->sections[secndx]->get_name()<<" is both writeable and executable.  Program is inherently unsafe!"<<endl;
+		}
+
+		/* executable sections handled by zipr/spri. */
+        	if(elfiop->sections[secndx]->isExecutable()) 
+		{
+			cout<<"Skipping scoop for section (executable) "<<elfiop->sections[secndx]->get_name()<<endl;
+                	continue;
+		}
+		/* name */
+		string name=elfiop->sections[secndx]->get_name();
+
+		/* start address */
+		/*
+		auto startaddr=new AddressID_t();
+		assert(startaddr);
+		startaddr->setVirtualOffset( elfiop->sections[secndx]->get_address());
+		startaddr->setFileID(firp->getFile()->getBaseID());
+		firp->getAddresses().insert(startaddr);
+		*/
+		auto startaddr=firp->addNewAddress(firp->getFile()->getBaseID(), elfiop->sections[secndx]->get_address());
+
+		/* end */
+		/*
+		auto endaddr=new AddressID_t();
+		assert(endaddr);
+		endaddr->setVirtualOffset( elfiop->sections[secndx]->get_address() + elfiop->sections[secndx]->get_size()-1);
+		endaddr->setFileID(firp->getFile()->getBaseID());
+		firp->getAddresses().insert(endaddr);
+		*/
+		auto endaddr=firp->addNewAddress(firp->getFile()->getBaseID(), elfiop->sections[secndx]->get_address() + elfiop->sections[secndx]->get_size()-1);
+
+
+		string the_contents;
+		the_contents.resize(elfiop->sections[secndx]->get_size()); 
+		// deal with .bss segments that are 0 init'd.
+		if (elfiop->sections[secndx]->get_data()) 
+			the_contents.assign(elfiop->sections[secndx]->get_data(),elfiop->sections[secndx]->get_size());
+
+//		Type_t *chunk_type=NULL; /* FIXME -- need to figure out the type system for scoops, but NULL should remain valid */
+
+		/* permissions */
+		int permissions= 
+			( elfiop->sections[secndx]->isReadable() << 2 ) | 
+			( elfiop->sections[secndx]->isWriteable() << 1 ) | 
+			( elfiop->sections[secndx]->isExecutable() << 0 ) ;
+
+		bool is_relro=is_in_relro_segment(secndx);
+		scoops_detected++;
+		/*
+		DataScoop_t *newscoop=new DataScoop_t(max_base_id++, name, startaddr, endaddr, NULL, permissions, is_relro, the_contents);
+		assert(newscoop);
+		firp->getDataScoops().insert(newscoop);
+		*/
+		auto newscoop=firp->addNewDataScoop( name, startaddr, endaddr, NULL, permissions, is_relro, the_contents, max_base_id++ );
+		(void)newscoop; // just give it to the IR
+
+		cout<<"Allocated new scoop for section "<<name
+		    <<"("<<hex<<startaddr->getVirtualOffset()<<"-"
+		    <<hex<<endaddr->getVirtualOffset()<<")"
+		    <<" perms="<<permissions<<" relro="<<boolalpha<<is_relro<<endl;
+
+	}
+
+}
+
+void PopulateCFG::detect_scoops_in_code(FileIR_t *firp)
+{
+	// data for this function
+	auto already_scoopified=set<VirtualOffset_t>();
+
+	// only valid for arm64
+	if(firp->getArchitecture()->getMachineType() != admtAarch64) return;
+
+	// check each insn for an ldr with a pcrel operand.
+	for(auto insn : firp->getInstructions())
+	{
+		// look for ldr's with a pcrel operand
+		const auto d=DecodedInstruction_t::factory(insn);
+		if(d->getMnemonic()!="ldr") continue;	 // only valid on arm.
+		const auto op0=d->getOperand(0);
+		const auto op1=d->getOperand(1);
+	       	if( !op1->isPcrel()) continue;
+
+		// sanity check that it's a memory operation, and extract fields
+		assert(op1->isMemory());
+		const auto referenced_address=op1->getMemoryDisplacement();
+		const auto op0_str=op0->getString();
+		const auto referenced_size=  // could use API call?
+			op0_str[0]=='w' ? 4  : 
+			op0_str[0]=='x' ? 8  : 
+			op0_str[0]=='s' ? 4  : 
+			op0_str[0]=='d' ? 8  : 
+			op0_str[0]=='q' ? 16 : 
+			throw domain_error("Cannot decode instruction size");
+			;
+
+		// check if we've seen this address already
+		const auto already_seen_it=already_scoopified.find(referenced_address);
+		if(already_seen_it!=end(already_scoopified)) continue;
+
+		// not seen, add it
+		already_scoopified.insert(referenced_address);
+
+
+		// find section and sanity check.
+		const auto sec=elfiop->sections.findByAddress(referenced_address);
+		if(sec==nullptr) continue;
+
+		// only trying to do this for executable chunks, other code deals with
+		// scoops not in the .text section.
+		if(!sec->isExecutable()) continue;
+
+		const auto sec_data=sec->get_data();
+		const auto sec_start=sec->get_address();
+		const auto the_contents=string(&sec_data[referenced_address-sec_start],referenced_size);
+		const auto fileid=firp->getFile()->getBaseID();
+
+
+		/*
+		auto start_addr=new AddressID_t(BaseObj_t::NOT_IN_DATABASE,fileid,referenced_address);
+		assert(start_addr);
+		firp->getAddresses().insert(start_addr);
+
+		auto end_addr=new AddressID_t(BaseObj_t::NOT_IN_DATABASE,fileid,referenced_address+referenced_size-1);
+		assert(end_addr);
+		firp->getAddresses().insert(end_addr);
+		*/
+		auto start_addr=firp->addNewAddress(fileid,referenced_address);
+		auto end_addr  =firp->addNewAddress(fileid,referenced_address+referenced_size-1);
+
+		const auto name="data_in_text_"+to_string(referenced_address);
+		const auto permissions=0x4; /* R-- */
+		const auto is_relro=false;
+		/*
+		auto newscoop=new DataScoop_t(BaseObj_t::NOT_IN_DATABASE, name, start_addr, end_addr, NULL, permissions, is_relro, the_contents);
+		firp->getDataScoops().insert(newscoop);
+		*/
+		auto newscoop=firp->addNewDataScoop(name, start_addr, end_addr, NULL, permissions, is_relro, the_contents);
+		(void)newscoop;
+
+		cout<< "Allocated data in text segment "<<name<<"=("<<start_addr->getVirtualOffset()<<"-"
+		    << end_addr->getVirtualOffset()<<")"<<endl;
+	}
+}
+
+void PopulateCFG::fill_in_landing_pads(FileIR_t *firp)
+{
+	const auto eh_frame_rep_ptr = split_eh_frame_t::factory(firp);
+	// eh_frame_rep_ptr->parse(); already parsed now.
+	if(getenv("EHIR_VERBOSE"))
+		eh_frame_rep_ptr->print();
+	cout<<"Completed eh-frame parsing"<<endl;
+
+	map<Function_t*,set<Instruction_t*> > insns_to_add_to_funcs;
+
+	for(const auto t : firp->getInstructions())
+	{
+		if(t->getFunction()==NULL)
+			continue;
+		auto lp=eh_frame_rep_ptr->find_lp(t);
+		if(lp && lp->getFunction()==NULL)
+			insns_to_add_to_funcs[t->getFunction()].insert(lp);
+	};
+
+
+	for(const auto & p : insns_to_add_to_funcs)
+	{
+		auto & func=p.first; 	
+		auto insns=p.second; 	/* copy */
+		auto insn_count=0;
+
+		while(insns.size()>0 )
+		{
+			auto it=insns.begin();
+			auto insn=*it;
+			insns.erase(it);
+
+			assert(insn);
+			if(insn->getFunction()!=NULL)
+				continue;
+
+			auto lp=eh_frame_rep_ptr->find_lp(insn);
+			if(lp && lp->getFunction()==NULL)
+				insns.insert(lp);
+
+			insn->setFunction(func);
+			cout<<"	Adding "<<insn->getBaseID()<<":"<<insn->getDisassembly()<<"@"<<hex<<insn->getAddress()->getVirtualOffset()<<dec<<endl;
+			insn_count++;
+			
+
+			auto target=insn->getTarget();
+			auto fallthru=insn->getFallthrough();
+
+			if(target) insns.insert(target);
+			if(fallthru) insns.insert(fallthru);
+		}
+		cout<<"Found LP outside of function "<<func->getName()<<" added "<<insn_count<<" instructions"<<endl;
+	};
+	
+}
+
+int PopulateCFG::parseArgs(const vector<string> step_args)
+{   
+    if(step_args.size()<1)
+    {
+            cerr<<"Usage: <id> [--fix-landing-pads | --no-fix-landing-pads]"<<endl;
+            return -1;
+    }
+
+    variant_id = stoi(step_args[0]);
+    
+    for (unsigned int i = 1; i < step_args.size(); ++i)
+    {
+            if (step_args[i]=="--fix-landing-pads")
+            {
+                    fix_landing_pads = true;
+            }
+            else if (step_args[i]=="--no-fix-landing-pads")
+            {
+                    fix_landing_pads = false;
+            }
+    }
+
+    cout<<"fix_landing_pads="<<fix_landing_pads<<endl;
+    
+    return 0;
+}
+
+int PopulateCFG::executeStep(IRDBObjects_t *const irdb_objects)
+{
+	try 
+	{
+		const auto pqxx_interface = irdb_objects->getDBInterface();
+		// now set the DB interface for THIS PLUGIN LIBRARY -- VERY IMPORTANT
+		BaseObj_t::setInterface(pqxx_interface);	
+
+		const auto variant = irdb_objects->addVariant(variant_id);
+		for(File_t* file : variant->getFiles())
+		{
+			const auto firp = irdb_objects->addFileIR(variant_id, file->getBaseID());
+			assert(firp);
+                        cout<<"Filling in cfg for "<<firp->getFile()->getURL()<<endl;
+
+			/* get the OID of the file */
+			const int elfoid=firp->getFile()->getELFOID();
+
+			pqxx::largeobject lo(elfoid);
+                	lo.to_file(pqxx_interface->getTransaction(),"readeh_tmp_file.exe");
+
+			elfiop.reset(new exeio());
+			elfiop->load(string("readeh_tmp_file.exe"));
+
+			fill_in_cfg(firp);
+			fill_in_scoops(firp);
+			detect_scoops_in_code(firp);
+
+			if (fix_landing_pads)
+			{
+				fill_in_landing_pads(firp);
+			}
+		}
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cerr<<"Unexpected database error: "<<pnide<<endl;
+		return -1;
+        }
+	catch(...)
+	{
+		cerr<<"Unexpected error"<<endl;
+		return -1;
+	}
+
+        cout<<"#ATTRIBUTE targets_set="<<targets_set<<endl;
+        cout<<"#ATTRIBUTE fallthroughs_set="<<fallthroughs_set<<endl;
+        cout<<"#ATTRIBUTE scoops_detected="<<scoops_detected<<endl;
+
+	if(getenv("SELF_VALIDATE"))
+	{
+		assert(targets_set > 10);
+		assert(fallthroughs_set > 100);
+		assert(scoops_detected > 5 );
+	}
+
+	return 0;
+}
+
+
+extern "C"
+shared_ptr<TransformStep_t> getTransformStep(void)
+{
+	const shared_ptr<TransformStep_t> the_step(new PopulateCFG());
+	return the_step;
+}
diff --git a/irdb-lib/ir_builders/fill_in_cfg.hpp b/irdb-lib/ir_builders/fill_in_cfg.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..93c36e48becad489a64b6fce26734a46b9335e77
--- /dev/null
+++ b/irdb-lib/ir_builders/fill_in_cfg.hpp
@@ -0,0 +1,95 @@
+#ifndef fill_in_cfg_hpp
+#define fill_in_cfg_hpp
+
+#include <irdb-core>
+#include <stdlib.h>
+#include <map>
+#include <exeio.h>
+
+class PopulateCFG : public IRDB_SDK::TransformStep_t
+{
+    public:
+        PopulateCFG(IRDB_SDK::DatabaseID_t p_variant_id = 0,
+                    bool p_fix_landing_pads = true
+            )
+            :
+            variant_id(p_variant_id),
+            fix_landing_pads(p_fix_landing_pads)
+        {
+		odd_target_count = 0;
+		bad_target_count = 0;
+		bad_fallthrough_count = 0;
+		failed_target_count = 0U;
+
+		targets_set=0;
+		fallthroughs_set=0;
+		scoops_detected=0;
+
+		elfiop = std::unique_ptr<EXEIO::exeio>(nullptr);
+        }
+
+	~PopulateCFG(void) override
+	{
+		// do nothing (this class uses shared IRDB objects that
+		// are not managed by this class).
+	}
+	
+	std::string getStepName(void) const override
+	{
+		return std::string("fill_in_cfg");
+	}
+        int parseArgs(const std::vector<std::string> step_args) override;
+	int executeStep(IRDB_SDK::IRDBObjects_t *const) override;
+    
+    private: // methods
+        
+        // main workers
+        void fill_in_cfg(IRDB_SDK::FileIR_t *);
+        void fill_in_scoops(IRDB_SDK::FileIR_t *);
+        void detect_scoops_in_code(IRDB_SDK::FileIR_t *firp);
+        void fill_in_landing_pads(IRDB_SDK::FileIR_t *);
+        
+        // helpers
+        void populate_instruction_map
+	(
+		std::map< std::pair<IRDB_SDK::DatabaseID_t,IRDB_SDK::VirtualOffset_t>, IRDB_SDK::Instruction_t*>&,
+		IRDB_SDK::FileIR_t *
+	);
+        
+        void set_fallthrough
+	(
+                std::map< std::pair<IRDB_SDK::DatabaseID_t,IRDB_SDK::VirtualOffset_t>, IRDB_SDK::Instruction_t*>&,
+                IRDB_SDK::DecodedInstruction_t *, IRDB_SDK::Instruction_t *, IRDB_SDK::FileIR_t *
+	);
+        
+        void set_target
+	(
+                std::map< std::pair<IRDB_SDK::DatabaseID_t,IRDB_SDK::VirtualOffset_t>, IRDB_SDK::Instruction_t*>&,
+                IRDB_SDK::DecodedInstruction_t *, IRDB_SDK::Instruction_t *, IRDB_SDK::FileIR_t *
+	);
+        
+        IRDB_SDK::File_t* find_file(IRDB_SDK::FileIR_t *, IRDB_SDK::DatabaseID_t);
+        void add_new_instructions(IRDB_SDK::FileIR_t *);
+        bool is_in_relro_segment(const int);
+    
+    private: //data
+        
+        // stats
+        int odd_target_count;
+        int bad_target_count;
+        int bad_fallthrough_count;
+        unsigned int failed_target_count;
+
+	size_t targets_set=0;
+	size_t fallthroughs_set=0;
+	size_t scoops_detected=0;
+        
+        // non-optional
+	IRDB_SDK::DatabaseID_t variant_id;        
+        bool fix_landing_pads;
+        
+        std::unique_ptr<EXEIO::exeio> elfiop;
+        std::set< std::pair<IRDB_SDK::DatabaseID_t,IRDB_SDK::VirtualOffset_t> > missed_instructions;
+};
+
+#endif
diff --git a/irdb-lib/ir_builders/fill_in_indtargs.cpp b/irdb-lib/ir_builders/fill_in_indtargs.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0eff242bbd708189b4cbe2a4613d418ed528669e
--- /dev/null
+++ b/irdb-lib/ir_builders/fill_in_indtargs.cpp
@@ -0,0 +1,3761 @@
+
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <irdb-core>
+#include <irdb-util>
+#include <iostream>
+#include <fstream>
+#include <limits>
+#include <string>
+#include <algorithm>
+#include <stdlib.h>
+#include <string.h>
+#include <map>
+#include <assert.h>
+#include <sys/mman.h>
+#include <sys/types.h>
+#include <regex.h>
+#include <ctype.h>
+#include <list>
+#include <stdio.h>
+#include <elf.h>
+
+#include <exeio.h>
+#include "check_thunks.hpp"
+#include "fill_in_indtargs.hpp"
+#include "libMEDSAnnotation.h"
+
+using namespace IRDB_SDK;
+using namespace std;
+using namespace EXEIO;
+using namespace MEDS_Annotation;
+
+
+/*
+ * defines 
+ */
+#define ALLOF(a) begin(a),end(a)
+
+extern void read_ehframe(FileIR_t* firp, EXEIO::exeio* );
+
+
+
+class PopulateIndTargs_t : public TransformStep_t
+{
+
+// record all full addresses and page-addresses found per function (or null for no function
+using PerFuncAddrSet_t=set<VirtualOffset_t>;
+map<Function_t*,PerFuncAddrSet_t> all_adrp_results;
+map<Function_t*,PerFuncAddrSet_t> all_add_adrp_results;
+
+// record all full addresses and page-addresses found that are spilled to the stack
+using SpillPoint_t = pair<Function_t*, VirtualOffset_t>;
+map<SpillPoint_t,PerFuncAddrSet_t> spilled_add_adrp_results;
+map<SpillPoint_t,PerFuncAddrSet_t> spilled_adrps;
+
+// record all full addresses found that are spilled to to a floating-point register (e.g., D10) 
+using DregSpillPoint_t = pair<Function_t*, string>;
+map<DregSpillPoint_t, PerFuncAddrSet_t> spilled_to_dreg;
+
+map<string,PerFuncAddrSet_t> per_reg_add_adrp_results;
+
+public:
+
+
+/* 
+ * class variables 
+ */
+
+
+// the bounds of the executable sections in the pgm.
+set< pair <VirtualOffset_t,VirtualOffset_t>  > bounds;
+
+// the set of (possible) targets we've found.
+map<VirtualOffset_t,ibt_provenance_t> targets;
+
+// the set of ranges represented by the eh_frame section, could be empty for non-elf files.
+set< pair< VirtualOffset_t, VirtualOffset_t> > ranges;
+
+// a way to map an instruction to its set of (direct) predecessors. 
+map< Instruction_t* , InstructionSet_t > preds;
+
+// keep track of jmp tables
+map< Instruction_t*, fii_icfs > jmptables;
+
+// a map of virtual offset -> instruction for quick access.
+map<VirtualOffset_t,Instruction_t*> lookupInstructionMap;
+
+// the set of things that are partially unpinned already.
+set<Instruction_t*> already_unpinned;
+
+long total_unpins=0;
+
+void range(VirtualOffset_t start, VirtualOffset_t end)
+{ 	
+	pair<VirtualOffset_t,VirtualOffset_t> foo(start,end);
+	ranges.insert(foo);
+}
+
+
+/*   
+ * is_in_range - determine if an address is referenced by the eh_frame section 
+ */
+bool is_in_range(VirtualOffset_t p)
+{
+	for(auto  bound : ranges)
+	{
+		auto start=bound.first;
+		auto end=bound.second;
+		if(start<=p && p<=end)
+			return true;
+	}
+	return false;
+}
+
+/*
+ * process_range -  do nothing now -- fix calls deals with this.
+ */
+void process_ranges(FileIR_t* firp)
+{
+
+}
+
+bool possible_target(VirtualOffset_t p, VirtualOffset_t from_addr, ibt_provenance_t prov)
+{
+	if(is_possible_target(p,from_addr))
+	{
+		if(getenv("IB_VERBOSE")!=nullptr)
+		{
+			if(from_addr!=0)
+				cout<<"Found IB target address 0x"<<std::hex<<p<<" at 0x"<<from_addr<<std::dec<<", prov="<<prov<<endl;
+			else
+				cout<<"Found IB target address 0x"<<std::hex<<p<<" from unknown location, prov="<<prov<<endl;
+		}
+		targets[p].add(prov);
+		return true;
+	}
+	return false;
+}
+
+bool is_possible_target(VirtualOffset_t p, VirtualOffset_t addr)
+{
+	for(auto bound : bounds)
+	{
+		auto start=bound.first;
+		auto end=bound.second;
+		if(start<=p && p<=end)
+		{
+			return true;
+		}
+        }
+	return false;
+
+}
+
+EXEIO::section*  find_section(VirtualOffset_t addr, EXEIO::exeio *elfiop)
+{
+         for ( int i = 0; i < elfiop->sections.size(); ++i )
+         {   
+                 EXEIO::section* pSec = elfiop->sections[i];
+                 assert(pSec);
+                 if(pSec->get_address() > addr)
+                         continue;
+                 if(addr >= pSec->get_address()+pSec->get_size())
+                         continue;
+
+                 return pSec;
+	}
+	return nullptr;
+}
+
+void handle_argument(
+		     const DecodedInstruction_t& decoded_insn, 
+		     const DecodedOperand_t &arg, 
+		     Instruction_t* insn, 
+		     ibt_provenance_t::provtype_t pt = ibt_provenance_t::ibtp_text
+		    )
+{
+	if(arg.isMemory() && decoded_insn.getMnemonic()=="lea") 
+	{
+		if(arg.isPcrel()) 
+		{
+			assert(insn);
+			assert(insn->getAddress());
+			possible_target(arg.getMemoryDisplacement() + insn->getAddress()->getVirtualOffset() +
+				insn->getDataBits().length(), insn->getAddress()->getVirtualOffset(), pt);
+		}
+		else
+		{
+			possible_target(arg.getMemoryDisplacement(), insn->getAddress()->getVirtualOffset(), pt);
+		}
+	}
+}
+
+
+void lookupInstruction_init(FileIR_t *firp)
+{
+	lookupInstructionMap.clear();
+	for(auto insn : firp->getInstructions())
+        {
+		const auto addr=insn->getAddress()->getVirtualOffset();
+		lookupInstructionMap[addr]=insn;
+	}
+}
+
+Instruction_t *lookupInstruction(FileIR_t *firp, VirtualOffset_t virtual_offset)
+{
+	if(lookupInstructionMap.find(virtual_offset)!=lookupInstructionMap.end())
+		return lookupInstructionMap[virtual_offset];
+	return nullptr;
+}
+
+void mark_targets(FileIR_t *firp)
+{
+        for(auto insn : firp->getInstructions())
+	{
+		auto addr=insn->getAddress()->getVirtualOffset();
+
+		/* lookup in the list of targets */
+		if(targets.find(addr)!=targets.end())
+		{
+			const auto isret=targets[addr].areOnlyTheseSet(ibt_provenance_t::ibtp_ret);
+			const auto isprintf=targets[addr].areOnlyTheseSet(ibt_provenance_t::ibtp_stars_data|ibt_provenance_t::ibtp_texttoprintf);
+			if (isret)
+			{
+				if(getenv("IB_VERBOSE")!=nullptr)
+					cout<<"Skipping pin for ret at "<<hex<<addr<<endl;
+			}
+			else if(isprintf)
+			{
+				if(getenv("IB_VERBOSE")!=nullptr)
+					cout<<"Skipping pin for text to printf at "<<hex<<addr<<endl;
+			}
+			else
+			{
+				if(getenv("IB_VERBOSE")!=nullptr)
+					cout<<"Setting pin at "<<hex<<addr<<endl;
+				/*
+				AddressID_t* newaddr = new AddressID_t;
+				newaddr->SetFileID(insn->getAddress()->getFileID());
+				newaddr->setVirtualOffset(insn->getAddress()->getVirtualOffset());
+				firp->getAddresses().insert(newaddr);
+				*/
+				auto newaddr=firp->addNewAddress(insn->getAddress()->getFileID(), insn->getAddress()->getVirtualOffset());
+				insn->setIndirectBranchTargetAddress(newaddr);
+			}
+		}
+	}
+}
+
+
+bool CallToPrintfFollows(FileIR_t *firp, Instruction_t* insn, const string& arg_str)
+{
+	for(auto ptr=insn->getFallthrough(); ptr!=nullptr; ptr=ptr->getFallthrough())
+	{
+		auto d=DecodedInstruction_t ::factory(ptr);
+		if(d->getMnemonic() == string("call"))
+		{
+			// check we have a target
+			if(ptr->getTarget()==nullptr)
+				return false;
+
+			// check the target has a function 
+			if(ptr->getTarget()->getFunction()==nullptr)
+				return false;
+
+			// check if we're calling printf.
+			if(ptr->getTarget()->getFunction()->getName().find("printf")==string::npos)
+				return false;
+
+			// found it
+			return true;
+		}
+
+		// found reference to argstring, assume it's a write and exit
+		if(d->getDisassembly().find(arg_str)!= string::npos)
+			return false;
+	}
+
+	return false;
+}
+
+bool texttoprintf(FileIR_t *firp,Instruction_t* insn)
+{
+	string dst="";
+	// note that dst is an output parameter of IsParameterWrite and an input parameter to CallFollows
+	if(isParameterWrite(firp,insn, dst) && CallToPrintfFollows(firp,insn,dst))
+	{
+		return true;
+	}
+	return false;
+}
+
+void get_instruction_targets(FileIR_t *firp, EXEIO::exeio* elfiop, const set<VirtualOffset_t>& thunk_bases)
+{
+
+        for(auto insn : firp->getInstructions())
+        {
+		auto disasm=DecodedInstruction_t::factory(insn);
+                VirtualOffset_t instr_len = disasm->length(); // Disassemble(insn,disasm);
+
+                assert(instr_len==insn->getDataBits().size());
+
+		const auto mt=firp->getArchitecture()->getMachineType();
+
+		if(mt==admtX86_64 || mt==admtI386)
+		{
+			// work for both 32- and 64-bit.
+			check_for_PIC_switch_table32_type2(firp, insn, *disasm, elfiop, thunk_bases);
+			check_for_PIC_switch_table32_type3(firp, insn, *disasm, elfiop, thunk_bases);
+
+			if (firp->getArchitectureBitWidth()==32)
+				check_for_PIC_switch_table32(firp, insn, *disasm, elfiop, thunk_bases);
+			else if (firp->getArchitectureBitWidth()==64)
+				check_for_PIC_switch_table64(firp, insn, *disasm, elfiop);
+			else
+				assert(0);
+
+			check_for_nonPIC_switch_table(firp, insn, *disasm, elfiop);
+			check_for_nonPIC_switch_table_pattern2(firp, insn, *disasm, elfiop);
+		}
+		else if(mt==admtAarch64)
+		{
+			check_for_arm_switch_type1(firp,insn,  *disasm, elfiop);
+		}
+		else
+			throw invalid_argument("Cannot determine machine type");
+
+		/* other branches can't indicate an indirect branch target */
+		if(disasm->isBranch()) // disasm.Instruction.BranchType)
+			continue;
+
+		ibt_provenance_t::provtype_t prov=0;
+		if(!texttoprintf(firp,insn))
+		{
+			prov=ibt_provenance_t::ibtp_text;
+		}
+		else
+		{
+			cout<<"TextToPrintf analysis of '"<<disasm->getDisassembly()<<"' successful at " <<hex<<insn->getAddress()->getVirtualOffset()<<endl;
+			prov=ibt_provenance_t::ibtp_texttoprintf;
+		}
+		/* otherwise, any immediate is a possible branch target */
+		for(const auto& op: disasm->getOperands())
+		{
+			if(op->isConstant())
+				possible_target(op->getConstant(), 0, prov);
+		}
+
+		for(auto i=0;i<4;i++)
+		{
+			if(disasm->hasOperand(i))
+			{
+				const auto op=disasm->getOperand(i);
+				handle_argument(*disasm, *op, insn, prov);
+			}
+		}
+	}
+}
+
+void get_executable_bounds(FileIR_t *firp, const section* shdr)
+{
+
+	/* not a loaded section */
+	if( !shdr->isLoadable()) 
+		return;
+
+	/* loaded, and contains instruction, record the bounds */
+	if( !shdr->isExecutable() )
+		return;
+
+	VirtualOffset_t first=shdr->get_address();
+	VirtualOffset_t second=shdr->get_address()+shdr->get_size();
+
+	bounds.insert(pair<VirtualOffset_t,VirtualOffset_t>(first,second));
+
+
+}
+
+void infer_targets(FileIR_t *firp, section* shdr)
+{
+//	int flags = shdr->get_flags();
+
+	if( ! shdr->isLoadable()) // (flags & SHF_ALLOC) != SHF_ALLOC)
+		/* not a loaded section */
+		return;
+
+	if( shdr->isExecutable() ) //(flags & SHF_EXECINSTR) == SHF_EXECINSTR)
+		/* loaded, but contains instruction.  we'll look through the VariantIR for this section. */
+		return;
+
+	/* if the type is NOBITS, then there's no actual data to look through */
+	if(shdr->isBSS() ) // get_type()==SHT_NOBITS)
+		return;
+
+
+	cout<<"Checking section "<<shdr->get_name() <<endl;
+
+	const char* data=shdr->get_data() ; // C(char*)malloc(shdr->sh_size);
+
+	assert(arch_ptr_bytes()==4 || arch_ptr_bytes()==8);
+	for(auto i=0u;i+arch_ptr_bytes()<=(size_t)shdr->get_size();i++)
+	{
+		// even on 64-bit, pointers might be stored as 32-bit, as a 
+		// elf object has the 32-bit limitations.
+		// there's no real reason to look for 64-bit pointers 
+		uintptr_t p=0;
+		if(arch_ptr_bytes()==4)
+			p=*(int*)&data[i];
+		else
+			p=*(VirtualOffset_t*)&data[i];	// 64 or 32-bit depending on sizeof uintptr_t, may need porting for cross platform analysis.
+
+
+
+		ibt_provenance_t prov;
+		if(shdr->get_name()==".init_array")
+			prov=ibt_provenance_t::ibtp_initarray;
+		else if(shdr->get_name()==".fini_array")
+			prov=ibt_provenance_t::ibtp_finiarray;
+		else if(shdr->get_name()==".got.plt")
+			prov=ibt_provenance_t::ibtp_gotplt;
+		else if(shdr->get_name()==".got")
+			prov=ibt_provenance_t::ibtp_got;
+		else if(shdr->get_name()==".dynsym")
+			prov=ibt_provenance_t::ibtp_dynsym;
+		else if(shdr->get_name()==".symtab")
+			prov=ibt_provenance_t::ibtp_symtab;
+		else if(shdr->isWriteable()) 
+			prov=ibt_provenance_t::ibtp_data;
+		else
+			prov=ibt_provenance_t::ibtp_rodata;
+
+		possible_target(p, i+shdr->get_address(), prov);
+
+	}
+
+}
+
+void handle_scoop_scanning(FileIR_t* firp)
+{
+	// check for addresses in scoops in the text section. 
+	for(auto scoop : firp->getDataScoops())
+	{
+		// test if scoop was added by fill_in_cfg -- make this test better.
+		if(scoop->getName().find("data_in_text_")==string::npos) continue;
+
+
+		// at the moment, FIC only creates 4-, 8-, and 16- bytes scoops
+		// change this code if FIC chagnes.
+		if(scoop->getSize() == 4 ) 
+		{
+			// may be a 4-byter, which can't hold an address.
+			continue; 
+		}
+		if(scoop->getSize() == 8 )
+		{
+			// check to see if the scoop has an IBTA 
+			const auto addr=*(uint64_t*)(scoop->getContents().c_str());
+			possible_target(addr, scoop->getStart()->getVirtualOffset(), ibt_provenance_t::ibtp_unknown);
+		}
+		else
+		{
+			// we may see 16 indicating that a ldr q-word happened.
+			// this isn't likely an IBT, so we skip scanning it.
+			assert(scoop->getSize() == 16 );	 
+		}
+	}
+}
+
+
+
+void print_targets()
+{
+	int j=1;
+	for(auto  p : targets )
+	{
+		const auto target=p.first;
+	
+		cout<<hex<<target;
+		if(j%10 == 0)
+			cout<<endl; 
+		else
+			cout<<", ";
+		j++;
+	}
+
+	cout<<endl;
+}
+
+set<Instruction_t*> find_in_function(string needle, Function_t *haystack)
+{
+	regex_t preg;
+	set<Instruction_t*> found_instructions;
+
+	assert(0 == regcomp(&preg, needle.c_str(), REG_EXTENDED));
+
+	for (auto candidate :  haystack->getInstructions())
+	{
+		auto disasm=DecodedInstruction_t::factory(candidate);
+
+		// check it's the requested type
+		if(regexec(&preg, disasm->getDisassembly().c_str(), 0, nullptr, 0) == 0)
+		{
+			found_instructions.insert(candidate);
+		}
+	}
+	regfree(&preg);
+	return found_instructions;
+}
+
+
+
+bool backup_until(const string &insn_type_regex_str, 
+		  Instruction_t *& prev, 
+		  Instruction_t* orig, 
+		  const string & stop_if_set="", 
+		  bool recursive=false, 
+		  uint32_t max_insns=10000u, 
+		  uint32_t max_recursions=5u)
+{
+
+	const auto find_or_build_regex=[&] (const string& s) -> regex_t&
+		{
+			// declare a freer for regexs so they go away when the program ends.
+			const auto regex_freer=[](regex_t* to_free)  -> void
+			{
+				regfree(to_free);
+				delete to_free;
+			};
+			// keep the map safe from anyone but me using it.
+			using regex_unique_ptr_t=unique_ptr<regex_t, decltype(regex_freer)>;
+			static map<string, regex_unique_ptr_t > regexs_used;
+
+			if(s=="")
+			{
+				static regex_t empty;
+				return empty;
+			}
+			const auto it=regexs_used.find(s);
+			if(it==regexs_used.end())
+			{
+				// allocate a new regex ptr
+				regexs_used.insert(pair<string,regex_unique_ptr_t>(s,move(regex_unique_ptr_t(new regex_t, regex_freer))));
+				// and compile it.
+				auto &regex_ptr=regexs_used.at(s);
+				const auto ret=regcomp(regex_ptr.get(), s.c_str(), REG_EXTENDED);
+				// error check
+				assert(ret==0);
+			}
+			return *regexs_used.at(s).get();
+		};
+
+
+	// build regexs.
+	const auto &preg            = find_or_build_regex(insn_type_regex_str);
+	const auto &stop_expression = find_or_build_regex(stop_if_set);
+
+
+	prev=orig;
+	while(preds[prev].size()==1 && max_insns > 0)
+	{
+		// dec max for next loop 
+		max_insns--;
+
+		// get the only item in the list.
+		prev=*(preds[prev].begin());
+	
+
+       		// get I7's disassembly
+		const auto disasm=DecodedInstruction_t::factory(prev);
+
+       		// check it's the requested type
+       		if(regexec(&preg, disasm->getDisassembly().c_str(), 0, nullptr, 0) == 0)
+			return true;
+
+		if(stop_if_set!="")
+		{
+			for(const auto operand : disasm->getOperands())
+			{
+				if(operand->isWritten() && regexec(&stop_expression, operand->getString().c_str(), 0, nullptr, 0) == 0)
+					return false;
+			}
+		}
+
+		// otherwise, try backing up again.
+	}
+	if(recursive && max_insns > 0 && max_recursions > 0 )
+	{
+		const auto myprev=prev;
+		// can't just use prev because recursive call will update it.
+		const auto &mypreds=preds[myprev];
+		for(const auto pred : mypreds)
+		{
+			prev=pred;// mark that we are here, in case we return true here.
+			const auto disasm=DecodedInstruction_t::factory(pred);
+       			// check it's the requested type
+       			if(regexec(&preg, disasm->getDisassembly().c_str(), 0, nullptr, 0) == 0)
+				return true;
+			if(stop_if_set!="")
+			{
+				for(const auto operand : disasm->getOperands())
+				{
+					if(operand->isWritten() && regexec(&stop_expression, operand->getString().c_str(), 0, nullptr, 0) == 0)
+						return false;
+				}
+			}
+			if(backup_until(insn_type_regex_str, prev, pred, stop_if_set, recursive, max_insns, max_recursions/mypreds.size()))
+				return true;
+
+			// reset for next call
+			prev=myprev;
+		}
+	}
+	return false;
+}
+
+
+
+void check_for_arm_switch_type1(
+		FileIR_t *firp, 
+		Instruction_t* i10, 
+		const DecodedInstruction_t &d10, 
+		EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type1;
+
+#if 0
+Sample code for this branch type:
+
+       ; x2 gets the value of x0
+       ; this probably is not normal or required, but we are not checking 
+       ; it anyhow.  This is just to understand the example.
+
+i1:    0x4039c4:    cmp     table_index_reg, #0x3
+i2:    0x4039c8:    b.hi    0x4039d4	 ; may also be a b.ls
+
+       // generate switch table base address
+       // this code may be hard to find if the compiler optimizes it
+       // outside the block with the rest of the dispatch code, and/or
+       // spills a register.
+       // thus, we allow for it not to be found, and instead us any "unk"
+       // we return true if we've found the entry to avoid looking at unks
+       // if we don't need to.
+i5:    0x40449c:    adrp    table_page_reg, 0x415000          // table page 
+i6:    0x4044a0:    add     table_base_reg, table_page_reg, #0x2b0 // table offset 
+       // table=table_page+table_offset
+       //
+       // load from switch table
+i7:    0x4044a4:    ldrh    table_entry_reg, [table_base_reg,table_index_reg,uxtw #1]
+or
+i7:    0x4044a4:    ldrb    table_entry_reg, [table_base_reg,table_index_reg,uxtw ]
+
+       // calculate branch_addr+4+table[i]*4
+i8:    0x4044a8:    adr     branch_reg, 0x4044b4 // jump base addr
+i9:    0x4044ac:    add     i10_reg, branch_reg, table_entry_reg, sxth #2
+       // actually take the branch
+i10:   0x4044b0:    br      i10_reg
+i11:   0x4044b4:    
+
+
+notes:
+
+1) jump table entries are 2-bytes
+2) jump table entries specify an offset from the byte after dispatch branch
+3) jump table entries dont store the lower 2 bits of the offset, as they 
+   have to be 0 due to instruction alignment
+
+	
+#endif
+	// sanity check the jump 
+        if(d10.getMnemonic() != "br") return;
+
+	// grab the reg
+	const auto i10_reg=d10.getOperand(0)->getString();
+
+	// try to find I9
+	auto i9=(Instruction_t*)nullptr;
+	/* search for externder=sxth or sxtb */
+	if(!backup_until( string()+"(add "+i10_reg+",.* sxth #2)|(add "+i10_reg+",.* sxtb #2)", /* look for this pattern. */
+				i9,                            /* find i9 */
+				i10,                           /* before I10 */
+				"^"+i10_reg+"$"                /* stop if i10_reg set */
+				))
+	{
+		return; 
+	}
+
+	// Extract the I9 fields.
+	assert(i9);
+	const auto d9p             = DecodedInstruction_t::factory(i9);
+	const auto &d9             = *d9p;
+	const auto offset_reg      = d9.getOperand(1)->getString();
+	const auto table_entry_reg = d9.getOperand(2)->getString();
+
+
+	// try to find I8
+	auto i8=(Instruction_t*)nullptr;
+	if(!backup_until(string()+"adr "+offset_reg+",", /* look for this pattern. */
+				i8,                      /* find i8 */
+				i9,                      /* before I9 */
+				"^"+offset_reg+"$"       /* stop if offste_reg set */
+				))
+		return; 
+
+
+	// extract the I8 fields
+	assert(i8);
+	const auto d8p            = DecodedInstruction_t::factory(i8);
+	const auto &d8            = *d8p;
+	const auto jump_base_addr = d8.getOperand(1)->getConstant();
+
+	// try to find I7
+	auto i7=(Instruction_t*)nullptr;
+	if(!backup_until(string()+ "(ldrh "+table_entry_reg+",)|(ldrb "+table_entry_reg+",)", /* look for this pattern. */
+				i7,                                                           /* find i7 */
+				i9,                                                           /* before I9 */
+				"^"+table_entry_reg+"$"                                       /* stop if index_reg set */
+				))
+		return;
+
+
+	// extract the I7 fields
+	assert(i7);
+	const auto d7p              = DecodedInstruction_t::factory(i7);
+	const auto &d7              = *d7p;
+	const auto memory_op_string = d7.getOperand(1)->getString();
+	const auto plus_pos         = memory_op_string.find(" +");
+	const auto table_base_reg   = memory_op_string.substr(0,plus_pos);
+	const auto table_index_reg  = memory_op_string.substr(plus_pos+3);
+	const auto table_entry_size = 
+		d7.getMnemonic()=="ldrb" ? 1 :
+		d7.getMnemonic()=="ldrh" ? 2 :
+		throw invalid_argument("Unable to detected switch table entry size for ARM64");
+
+	// now we try to find the table base in I5 and I6
+	// but we may fail due to compiler opts.  Prepare for such failures
+	// by creating a set of possible table bases.
+	// If we find i5/i6 or a reload of a spilled table address,
+	// we will refine our guess.
+	auto all_table_bases= per_reg_add_adrp_results[table_base_reg];
+
+	// try to find I6
+	auto i6=(Instruction_t*)nullptr;
+	if(backup_until(string()+"add "+table_base_reg+",",  /* look for this pattern. */
+	                i6,                                  /* find i6 */
+	                i7,                                  /* before I7 */
+	                "^"+table_base_reg+"$",              /* stop if table_base_reg set */
+	                true,			             /* look hard -- recursely examine up to 10k instructions and 500 blocks */
+	                10000,
+	                500
+			))
+	{
+
+
+		// extract the I6 fields
+		assert(i6);
+		const auto d6p                = DecodedInstruction_t::factory(i6);
+		const auto &d6                = *d6p;
+		const auto table_page_reg    = d6.getOperand(1)->getString();
+		const auto table_page_offset = d6.getOperand(2)->getConstant();
+
+		// try to find I5
+		auto i5=(Instruction_t*)nullptr;
+		if(backup_until(string()+"adrp "+table_page_reg+",",  /* look for this pattern. */
+		                i5,                                   /* find i5 */
+		                i6,                                   /* before I6 */
+		                "^"+table_page_reg+"$",               /* stop if table_page set */
+		                true,			              /* look hard -- recursely examine up to 10k instructions and 500 blocks */
+		                10000,
+		                500
+		                ))
+		{
+			// extract i5 fields
+			assert(i5);
+			const auto d5p        = DecodedInstruction_t::factory(i5);
+			const auto &d5        = *d5p;
+			const auto table_page = d5.getOperand(1)->getConstant();
+			const auto table_addr=table_page+table_page_offset;
+			all_table_bases= PerFuncAddrSet_t({table_addr});
+		}
+		else
+		{
+			for(auto adrp_value : all_adrp_results[i10->getFunction()])
+			{
+				all_table_bases.insert(adrp_value+table_page_offset);
+			}
+		}
+	}
+	// could not find i5/i6, it's possible (likely) that the table was just spilled and is being
+	// reloaded from the stack.  check for that.
+	else if(backup_until(string()+"ldr "+table_base_reg+",",  /* look for this pattern. */
+	                     i6,                                  /* find i6 -- the reload of the table */
+	                     i7,                                  /* before I7 */
+	                     "^"+table_base_reg+"$",              /* stop if table_base_reg set */
+	                     true,                                /* look hard -- recursely examine up to 10k instructions and 500 blocks */
+	                     10000,
+	                     500
+	                     ))
+	{
+		assert(i6);
+		const auto d6p                = DecodedInstruction_t::factory(i6);
+		const auto &d6                = *d6p;
+		// found reload of table address from spill location!
+                // reloads write to the stack with a constant offset.
+                const auto reload_op1=d6.getOperand(1);
+                assert(reload_op1->isMemory());
+                const auto reload_op1_string=reload_op1->getString();
+
+                // needs to have a base reg, which is either sp or x29
+                const auto hasbr   = (reload_op1->hasBaseRegister()) ;
+                const auto okbr    = (reload_op1_string.substr(0,2)=="sp" || reload_op1_string.substr(0,3)=="x29" ) ;
+                const auto hasdisp = (reload_op1->hasMemoryDisplacement()) ;
+                const auto hasir   = (reload_op1->hasIndexRegister()) ;
+		const auto ok      = hasbr && okbr && hasdisp && !hasir;
+
+		if(ok)
+		{
+			// extract fields
+			const auto reload_disp=reload_op1->getMemoryDisplacement();
+			const auto reload_loc=SpillPoint_t({i10->getFunction(),reload_disp});
+			const auto &spills=spilled_add_adrp_results[reload_loc];
+			if(spills.size()>0)  
+			{
+				all_table_bases=spills;
+				cout<<"Using spilled table bases from stack!"<<endl;
+			}
+		}
+
+	}
+	// also possible we couldn't find it spilled to the stack, and it's instead spilled to an FP register.
+	else if(backup_until(string()+"fmov "+table_base_reg+",",  /* look for this pattern. */
+	                     i6,                                   /* find i6 -- the reload of the table from an FP reg*/
+	                     i7,                                   /* before I7 */
+	                     "^"+table_base_reg+"$",               /* stop if table_base_reg set */
+	                     true,                                 /* look hard -- recursely examine up to 10k instructions and 500 blocks */
+	                     10000,
+	                     500
+	                     ))
+	{
+		assert(i6);
+		const auto d6p             = DecodedInstruction_t::factory(i6);
+		const auto &d6             = *d6p;
+                const auto reload_op1     = d6.getOperand(1);
+		const auto reload_op1_str = reload_op1->getString();
+		const auto is_dreg        = reload_op1_str[0]=='d';
+
+		if(is_dreg)
+		{
+
+			const auto reload_loc = DregSpillPoint_t({i6->getFunction(), reload_op1_str});
+			const auto spills     = spilled_to_dreg[reload_loc];
+			if(spills.size()>0)  
+			{
+				all_table_bases=spills;
+				cout<<"Using spilled table bases from d-reg!"<<endl;
+			}
+		}
+	}
+	// end trying to find the table base.
+
+	// try to find i1+i2 so we can assign a resonable bound on the switch table size.
+	// assume it's 1024 if we can't otherwise find it.
+	const auto max_bound=1024u;
+	auto my_bound=max_bound;
+
+	// start by finding i2.
+	auto i2=(Instruction_t*)nullptr;
+	if(backup_until(string()+"(b.hi)|(b.ls)", /* look for this pattern. */
+				i2,           /* find i2 */
+				i7,           /* before I7 */
+				"",           /* don't stop for reg sets, just look for control flow */
+				true	      /* recurse into other blocks */
+				))
+	{
+		/* find i1 */
+		auto i1=(Instruction_t*)nullptr;
+		if(backup_until(string()+"cmp ",                     /* look for this pattern. */
+					i1,                          /* find i1 */
+					i2,                          /* before I2 */
+					"(cmp)|(adds)|(subs)|(cmn)", /* stop for CC-setting insns -- fixme, probably not the right syntax for stop-if */
+					true	                     /* recurse into other blocks */
+					))
+		{
+			// try to verify that there's data flow from the ldr[bh] to the cmp 
+			auto next_reg=table_index_reg;
+			auto prev_insn=i7;
+			while(true)
+			{
+				auto new_i1=(Instruction_t*)nullptr;
+				if(backup_until(string()+"cmp "+next_reg+",", /* look for this pattern. */
+							new_i1,               /* find i1 */
+							prev_insn,            /* before prev_insn */
+							"^"+next_reg+"$",     /* stop if next_reg is set */
+							true	              /* recurse into other blocks */
+							))
+				{
+					if(i1!=new_i1) /* sanity check that we got to the same place */
+						break;
+					const auto d1    = DecodedInstruction_t::factory(i1);
+					const auto d1op1 =  d1->getOperand(1);
+					if(d1op1->isConstant())
+					{
+						my_bound=d1op1->getConstant();
+					}
+					break;
+
+				}
+				else if(backup_until(string()+"mov "+next_reg+",", /* look for this pattern. */
+							new_i1,                    /* find i1 */
+							prev_insn,                 /* before I2 */
+							"^"+next_reg+"$",          /* stop if next_reg is set */
+							true	                   /* recurse into other blocks */
+							))
+				{
+					// track backwards on reg 2 if we find a mov <reg1>, <reg2>
+					const auto d1        = DecodedInstruction_t::factory(new_i1);
+					const auto new_d1op1 = d1->getOperand(1);
+					if(new_d1op1->isRegister())
+					{
+						next_reg=new_d1op1->getString();
+						continue;
+					}
+					else
+					{
+						// movd constant into table reg?  wtf
+						break;
+					}
+				}
+				else
+				{
+					// no bound found
+					break;
+				}
+				assert(0);
+			}
+		}
+
+	}
+	
+	const auto do_verbose=getenv("IB_VERBOSE");
+
+	// given:
+	//   1) a set of possible places for a jump table (all_table_bases)
+	//   2) address from which the the tables is relative (jump_base_addr)
+	//   3) the size of the table (my_bound)
+	//
+	//   calculate any possible targets for this switch.
+
+	// consider each jump table
+	auto my_targets=set<VirtualOffset_t>();
+	auto valid_table_count=0u;
+	for(auto cur_table_addr : all_table_bases)
+	{
+
+		// try to find switch table jumps
+		const auto i10_func=i10->getFunction();
+
+		// find the section with the jump table
+		const auto table_section=find_section(cur_table_addr,elfiop);
+		if(!table_section) continue;  
+
+		// if the section has no data, abort if not found
+		const auto table_section_data_ptr=table_section->get_data();
+		if(table_section_data_ptr == nullptr ) continue;
+
+		// get the section's adddress, abort if not loaded
+		const auto table_section_address=table_section->get_address();
+		if(table_section_address==0) continue;
+	
+		// ARM swith tables are in ROdata, thus not exectuable and not writeable.
+		if( table_section->isExecutable() ) continue;
+		if( table_section->isWriteable() ) continue;
+
+		// calculate how far into the section the table is.
+		const auto table_offset_into_section=(cur_table_addr-table_section_address);
+
+		// calculate the actual data for the table
+		const auto table_data_ptr = table_section_data_ptr + table_offset_into_section;
+
+		// calculate a stop point so we don't fall out of the section.
+		const auto table_section_end_ptr=table_section_data_ptr+table_section->get_size();
+
+		// define how to map an index in the table into an address to deref.
+		const auto getEntryPtr  = [&](const uint64_t index) { return table_data_ptr + index*table_entry_size; };
+		const auto getEntryAddr = [&](const uint64_t index) { return cur_table_addr + index*table_entry_size; };
+
+		if(do_verbose)
+		{
+			// log that we've found a table, etc.
+			cout << "Found ARM type1 at 0x"<<hex<<i10->getAddress()->getVirtualOffset()
+			     << " with my_bound = 0x"<<hex<<my_bound
+			     << ", table_entry_size = "<<dec<<table_entry_size
+			     << ", jump_base_addr = 0x"<<hex<<jump_base_addr
+			     << ", table_base_reg='"<<table_base_reg<<"'"
+			     << ", table_index_reg='"<<table_index_reg<<"'"
+			     << ", table_addr="<<cur_table_addr
+			     << endl;
+		}
+
+		const auto do_verbose=getenv("IB_VERBOSE") != nullptr;
+
+		// look at each table entry
+		auto target_count=0U;
+		using OffOffProvTuple_t = tuple<VirtualOffset_t, VirtualOffset_t, ibt_provenance_t> ;
+		auto this_table_targets=vector<OffOffProvTuple_t>();
+		for ( ; getEntryPtr(target_count)+table_entry_size < table_section_end_ptr ; target_count++ )
+		{
+			const auto entry_ptr      = getEntryPtr(target_count);
+			const auto entry_address  = getEntryAddr(target_count);
+			const auto table_entry    = 
+				table_entry_size==1 ? *(int8_t* )entry_ptr :
+				table_entry_size==2 ? *(int16_t*)entry_ptr :
+				throw invalid_argument("Cannot determine how to load table entry from size");
+			const auto candidate_ibta = jump_base_addr+table_entry*4;	 // 4 being instruction alignment factor for ARM64
+			const auto ibtarget       = lookupInstruction(firp, candidate_ibta);
+
+			if(do_verbose)
+				cout << "\tEntry #"<<dec<<target_count<<"= ent-addr="<<hex<<entry_address
+				     << " ent="<<hex<<+table_entry	 // print as int, not char.
+				     << " ibta="<<candidate_ibta;
+
+			// stop if we failed to find an instruction,
+			// or find an instruction outside the function
+			if( ibtarget == nullptr )
+			{
+				if(do_verbose)
+					cout<<" -- no target insn!"<<endl;
+				break;
+			}
+			const auto ibtarget_func=ibtarget->getFunction();
+			if( i10_func == nullptr )
+			{
+				// finding switch in non-function is OK.
+			}
+			else if(ibtarget_func == nullptr )
+			{
+				// finding target in non-function is OK
+			}
+			else if( i10_func != ibtarget_func )
+			{
+				// finding switch in function to different function, not ok.
+				if(do_verbose)
+					cout<<" -- switch to diff func? No."<<endl;
+				break;
+				
+			}
+
+			// record that we found something that looks valid-enough to try to pin
+			// stop if we couldn't pin.
+			if(!is_possible_target(candidate_ibta,entry_address))
+			{
+				if(do_verbose)
+					cout<<" -- not valid target!"<<endl;
+				break;
+			}
+			if(firp->findScoop(candidate_ibta)!=nullptr)
+			{
+				if(do_verbose)
+					cout<<" -- not valid target due to data-in-text detection!"<<endl;
+				break;
+
+			}
+
+			if(do_verbose)
+				cout<<" -- valid target!"<<endl;
+
+			// record this entry of the table
+			// this works on newer compilers and is easier to read, but older compilers....
+			// this_table_targets.push_back({candidate_ibta, entry_address,prov});
+			this_table_targets.push_back(make_tuple(candidate_ibta, entry_address,prov));
+
+			if(target_count>my_bound)
+				break;
+
+		}
+		// allow this table if the bound was a max-bound situation.
+		// also allow if all the table entries were valid.
+		// (allow week off-by-one comparison due to inaccurancies in detecting exact bound)
+		if(my_bound == max_bound || target_count+1 >= my_bound)
+		{
+			// since this table is valid, add all entries to the list of IBT's for this IR.
+			for(auto &t : this_table_targets)
+			{
+				const auto candidate_ibta=get<0>(t);
+				possible_target(candidate_ibta, get<1>(t), get<2>(t));
+				my_targets.insert(candidate_ibta);
+			}
+			valid_table_count++;
+		}
+	}
+	cout  << "Across "<<dec<<all_table_bases.size()<< " tables, "<<valid_table_count<<" are valid, bound="<<my_bound
+	      << " unique target count="<<my_targets.size()<<" entry_size="<<table_entry_size<<endl;
+	return; 
+}
+
+
+/*
+ * check_for_PIC_switch_table32 - look for switch tables in PIC code for 32-bit code.
+ */
+void check_for_PIC_switch_table32(FileIR_t *firp, Instruction_t* insn, const DecodedInstruction_t& disasm, EXEIO::exeio* elfiop, const set<VirtualOffset_t> &thunk_bases)
+{
+
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type1;
+#if 0
+
+/* here's typical code */
+
+I1: 080a9037 <gedit_floating_slider_get_type+0x607> call   0806938e <_gedit_app_ready+0x8e>  	// ebx=080a903c
+I2: 080a903c <gedit_floating_slider_get_type+0x60c> add    $0x45fb8,%ebx			// ebx=<module_start>
+...
+I3: 080a90f8 <gedit_floating_slider_get_type+0x6c8> mov    -0x1ac14(%ebx,%esi,4),%eax		// table_start=<module_start-0x1ac14
+												// table_offset=eax=table_start[esi]
+I4: 080a90ff <gedit_floating_slider_get_type+0x6cf> add    %ebx,%eax				// switch_case=eax=<module_start>+table_offset
+I5: 080a9101 <gedit_floating_slider_get_type+0x6d1> jmp    *%eax				// jump switch_case
+...
+I6: 0806938e <_gedit_app_ready+0x8e> mov    (%esp),%ebx
+I7: 08069391 <_gedit_app_ready+0x91> ret
+
+
+/* However, since the thunk and the switch table can be (and sometimes are) very control-flow distinct, 
+ * we just collect all the places where a module can start by examining all the thunk/add pairs.
+ * After that, we look for all jumps that match the I3-I5 pattern, and consider the offset against each
+ * module start.  If we find that there are possible targets at <module_start>+table_offset, we record them.
+ */
+
+#endif
+
+        Instruction_t* I5=insn;
+        Instruction_t* Icmp=nullptr;
+        Instruction_t* I4=nullptr;
+        Instruction_t* I3=nullptr;
+        // check if I5 is a jump
+        if(disasm.getMnemonic() != "jmp")
+		return;
+
+	// return if it's a jump to a constant address, these are common
+        if(disasm.getOperand(0)->isConstant() )
+		return;
+
+	// return if it's a jump to a memory address
+        if(disasm.getOperand(0)->isMemory() )
+		return;
+
+	assert(disasm.getOperand(0)->isRegister());
+	const auto I5_reg=disasm.getOperand(0)->getString();
+	auto jmp_reg=string();
+	auto add_reg=string();
+
+	// has to be a jump to a register now
+
+	// backup and find the instruction that's an add before I8 
+	if(!backup_until(string()+"add "+I5_reg+"|lea "+I5_reg, I4, I5, I5_reg))
+	{
+		auto mov_insn=static_cast<Instruction_t*>(nullptr);
+		if(!backup_until(string()+"mov "+I5_reg, mov_insn, I5, I5_reg))
+			return;
+		const auto p_mov_insn_disasm=DecodedInstruction_t::factory(mov_insn);
+		const auto &mov_insn_disasm=*p_mov_insn_disasm;
+		if(!mov_insn_disasm.getOperand(1)->isRegister())
+			return;
+		const auto mov_reg=mov_insn_disasm.getOperand(1)->getString();
+		if(!backup_until(string()+"add "+mov_reg, I4, mov_insn, mov_reg))
+				return;
+		jmp_reg=mov_reg;
+	}
+	else 
+	{
+		const auto p_d4=DecodedInstruction_t::factory(I4);
+		const auto &d4=*p_d4;
+		if(d4.getMnemonic()=="lea")
+		{
+			const auto base_reg=d4.getOperand(1)->getBaseRegister();
+			switch(base_reg)
+			{
+				case 0/*REG0*/: jmp_reg="eax"; break;
+				case 1/*REG1*/: jmp_reg="ecx"; break;
+				case 2/*REG2*/: jmp_reg="edx"; break;
+				case 3/*REG3*/: jmp_reg="ebx"; break;
+				case 4/*REG4*/: jmp_reg="esp"; break;
+				case 5/*REG5*/: jmp_reg="ebp"; break;
+				case 6/*REG6*/: jmp_reg="esi"; break;
+				case 7/*REG7*/: jmp_reg="edi"; break;
+				default: 
+					// no base register;
+					return;
+			}
+			const auto index_reg=d4.getOperand(1)->getBaseRegister();
+			switch(index_reg)
+			{
+				case 0/*REG0*/: add_reg="eax"; break;
+				case 1/*REG1*/: add_reg="ecx"; break;
+				case 2/*REG2*/: add_reg="edx"; break;
+				case 3/*REG3*/: add_reg="ebx"; break;
+				case 4/*REG4*/: add_reg="esp"; break;
+				case 5/*REG5*/: add_reg="ebp"; break;
+				case 6/*REG6*/: add_reg="esi"; break;
+				case 7/*REG7*/: add_reg="edi"; break;
+				default: 
+					// no base register;
+					return;
+			}
+		}
+		else
+		{
+			jmp_reg=I5_reg;
+			if(!d4.getOperand(1)->isRegister())
+				return;
+			add_reg=d4.getOperand(1)->getString();
+		}
+	}
+
+	assert(jmp_reg!="" && add_reg!="" && I4!=nullptr);
+
+
+	// backup and find the instruction that's an movsxd before I7
+	if(!backup_until(string()+"(mov "+jmp_reg+"|mov "+add_reg+")", I3, I4))
+		return;
+
+	auto table_size = 0U;
+	if (!backup_until("cmp", Icmp, I3))
+	{
+		cerr<<"pic32: could not find size of switch table"<<endl;
+		table_size=std::numeric_limits<int>::max();
+		// set table_size to be very large, so we can still do pinning appropriately
+	}
+	else
+	{
+		//DISASM dcmp;
+		//Disassemble(Icmp,dcmp);
+		auto dcmp=DecodedInstruction_t::factory(Icmp);	
+		table_size = dcmp->getImmediate(); //Instruction.Immediat;
+		if(table_size<=0)
+			table_size=std::numeric_limits<int>::max();
+	}
+
+	// grab the offset out of the lea.
+	const auto p_d2=DecodedInstruction_t::factory(I3);
+	const auto &d2=*p_d2;
+
+	// get the offset from the thunk
+	auto table_offset=d2.getAddress(); 
+	if(table_offset==0)
+		return;
+
+	cout<<hex<<"Found switch dispatch at "<<I3->getAddress()->getVirtualOffset()
+	    << " with table_offset="<<table_offset <<" and table_size="<<table_size<<endl;
+		
+	/* iterate over all thunk_bases/module_starts */
+	for(auto thunk_base : thunk_bases)
+	{
+		VirtualOffset_t table_base=thunk_base+table_offset;
+
+		// find the section with the data table
+        	EXEIO::section *pSec=find_section(table_base,elfiop);
+		if(!pSec)
+			continue;
+
+		// if the section has no data, abort 
+        	const char* secdata=pSec->get_data();
+		if(!secdata)
+			continue;
+
+		// get the base offset into the section
+        	VirtualOffset_t offset=table_base-pSec->get_address();
+		int i;
+		for(i=0;i<3;i++)
+		{
+                	if((int)(offset+i*4+sizeof(int)) > (int)pSec->get_size())
+                        	break;
+
+                	const int *table_entry_ptr=(const int*)&(secdata[offset+i*4]);
+                	int table_entry=*table_entry_ptr;
+
+			if(!is_possible_target(thunk_base+table_entry,table_base+i*4))
+				break;	
+		}
+		/* did we finish the loop or break out? */
+		if(i==3)
+		{
+			set<Instruction_t *> ibtargets;
+
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"Found switch table (thunk-relative) at "<<hex<<table_base+table_offset<<endl;
+			// finished the loop.
+			for(i=0;true;i++)
+			{
+                		if((int)(offset+i*4+sizeof(int)) > (int)pSec->get_size())
+                        		break;
+	
+                		const int32_t *table_entry_ptr=(const int32_t*)&(secdata[offset+i*4]);
+                		VirtualOffset_t table_entry=*table_entry_ptr;
+	
+				if(getenv("IB_VERBOSE")!=0)
+					cout<<"Found switch table (thunk-relative) entry["<<dec<<i<<"], "<<hex<<thunk_base+table_entry<<endl;
+
+				if(!possible_target(thunk_base+table_entry,table_base+i*4,prov))
+					break;
+
+				auto ibtarget = lookupInstruction(firp, thunk_base+table_entry);
+				if (ibtarget && ibtargets.size() <= table_size)
+				{
+					ibtargets.insert(ibtarget);
+				}
+			}
+
+			// valid switch table? may or may not have default: in the switch
+			// table size = 8, #entries: 9 b/c of default
+			cout << "pic32 (base pattern): table size: " << table_size << " ibtargets.size: " << ibtargets.size() << endl;
+			jmptables[I5].addTargets(ibtargets);
+			if (table_size == ibtargets.size() || table_size == (ibtargets.size()-1))
+			{
+				cout << "pic32 (base pattern): valid switch table detected ibtp_switchtable_type1" << endl;
+				jmptables[I5].setAnalysisStatus(iasAnalysisComplete);
+			
+			}
+		}
+		else
+		{
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"Found that  "<<hex<<table_base+table_offset<<endl;
+		}
+
+		// now, try next thunk base 
+	}
+}
+
+
+
+void check_for_PIC_switch_table32_type2(FileIR_t *firp, Instruction_t* insn, const DecodedInstruction_t& disasm, EXEIO::exeio* elfiop, const set<VirtualOffset_t> &thunk_bases)
+{
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type2;
+	auto ibtargets = InstructionSet_t();
+#if 0
+
+/* here's typical code */
+I1:   0x8098ffc <text_handler+33>: cmp    eax,0x8
+I2:   0x8098fff <text_handler+36>: ja     0x8099067 <text_handler+140>
+I3:   0x8099001 <text_handler+38>: lea    ecx,[ebx-0x21620]
+I4:   0x8099007 <text_handler+44>: add    ecx,DWORD PTR [ebx+eax*4-0x21620]
+I5:   0x809900e <text_handler+51>: jmp    ecx
+#endif
+
+        Instruction_t* I5=insn;
+        Instruction_t* I4=nullptr;
+//        Instruction_t* I3=nullptr;
+        // check if I5 is a jump
+        if(strstr(disasm.getMnemonic().c_str() /*disasm.Instruction.Mnemonic*/, "jmp")==nullptr)
+		return;
+
+	// return if it's a jump to a constant address, these are common
+        if(disasm.getOperand(0)->isConstant() /*disasm.Argument1.ArgType&CONSTANT_TYPE*/)
+		return;
+
+	// return if it's a jump to a memory address
+        //if(disasm.Argument1.ArgType&MEMORY_TYPE)
+        if(disasm.getOperand(0)->isMemory())
+		return;
+
+	// has to be a jump to a register now
+
+	// backup and find the instruction that's an add before I8 
+	if(!backup_until("add", I4, I5))
+		return;
+
+	const auto d4=DecodedInstruction_t::factory(I4);
+	if(!d4->hasOperand(1) || !d4->getOperand(1)->isMemory())
+		return;
+
+	// found that sometimes I3 is set a different way, 
+	// and that it's perfectly reasonable to just use I4's offsets.
+	// backup and find the instruction that's an movsxd before I7
+//	if(!backup_until("lea", I3, I4))
+//		return;
+
+	// get the offset from the thunk
+	VirtualOffset_t table_offset=d4->getOperand(1)->getMemoryDisplacement(); 
+	if(table_offset==0)
+		return;
+
+	cout<<hex<<"Found (type2) switch dispatch at "<<I5->getAddress()->getVirtualOffset()<< " with table_offset="<<table_offset<<endl;
+		
+	/* iterate over all thunk_bases/module_starts */
+	for(auto thunk_base : thunk_bases )
+	{
+		auto table_base=thunk_base+table_offset;
+
+		// find the section with the data table
+        	auto pSec=find_section(table_base,elfiop);
+		if(!pSec)
+			continue;
+
+		// if the section has no data, abort 
+        	const auto secdata=pSec->get_data();
+		if(!secdata)
+			continue;
+
+		// get the base offset into the section
+        	VirtualOffset_t offset=table_base-pSec->get_address();
+		int i;
+		for(i=0;i<3;i++)
+		{
+                	if((int)(offset+i*4+sizeof(int)) > (int)pSec->get_size())
+                        	break;
+
+                	const int32_t *table_entry_ptr=(const int32_t*)&(secdata[offset+i*4]);
+                	VirtualOffset_t table_entry=*table_entry_ptr;
+
+// cout<<"Checking target base:" << std::hex << table_base+table_entry << ", " << table_base+i*4<<endl;
+			if(!is_possible_target(table_base+table_entry,table_base+i*4) && !is_possible_target(thunk_base+table_entry,table_base+i*4))
+				break;	
+		}
+		/* did we finish the loop or break out? */
+		if(i==3)
+		{
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"Found switch table (pic3, type2) (thunk-relative) at "<<hex<<table_base+table_offset<<endl;
+			// finished the loop.
+			for(i=0;true;i++)
+			{
+                		if((int)(offset+i*4+sizeof(int)) > (int)pSec->get_size())
+                        		break;
+	
+                		const int32_t *table_entry_ptr=(const int32_t*)&(secdata[offset+i*4]);
+                		VirtualOffset_t table_entry=*table_entry_ptr;
+	
+				if(getenv("IB_VERBOSE")!=0)
+					cout<<"Found switch table (thunk-relative) entry["<<dec<<i<<"], "<<hex<<table_base+table_entry<<" or "<<thunk_base+table_entry<<endl;
+				auto t1=possible_target(table_base+table_entry,table_base+i*4,prov);
+				auto t2=possible_target(thunk_base+table_entry,table_base+i*4,prov);
+				if(!t1 && !t2)
+					break;
+
+				auto ibtarget1 = lookupInstruction(firp, table_base+table_entry);
+				if (ibtarget1)
+					ibtargets.insert(ibtarget1);
+				auto ibtarget2 = lookupInstruction(firp, thunk_base+table_entry);
+				if (ibtarget2)
+					ibtargets.insert(ibtarget2);
+			}
+		}
+		else
+		{
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"Found that  "<<hex<<table_base+table_offset<<endl;
+		}
+
+		// now, try next thunk base 
+	}
+	jmptables[I5].addTargets(ibtargets);
+}
+
+
+/*
+ * Detects this type of switch:
+ *
+ * 	  0x809900e <text_handler+51>: jmp    [eax*4 + 0x8088208]
+ *
+ * nb: also works for 64-bit.
+ */
+void check_for_PIC_switch_table32_type3(FileIR_t* firp, Instruction_t* insn, const DecodedInstruction_t& disasm, EXEIO::exeio* elfiop, const set<VirtualOffset_t> &thunk_bases)
+{
+	uint32_t ptrsize=firp->getArchitectureBitWidth()/8;
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type3;
+
+        Instruction_t* I5=insn;
+        // check if I5 is a jump
+        if(strstr(disasm.getMnemonic().c_str(), "jmp")==nullptr)
+		return;
+
+	// return if it's not a jump to a memory address
+        if(!(disasm.getOperand(0)->isMemory()))
+		return;
+
+	/* return if there's no displacement */
+        if(disasm.getOperand(0)->getMemoryDisplacement()==0)
+		return;
+
+        if(!disasm.getOperand(0)->hasIndexRegister() || disasm.getOperand(0)->getScaleValue()!=ptrsize)
+		return;
+
+	// grab the table base out of the jmp.
+	VirtualOffset_t table_base=disasm.getOperand(0)->getMemoryDisplacement();
+	if(disasm.getOperand(0)->isPcrel())
+		table_base+=insn->getDataBits().size()+insn->getAddress()->getVirtualOffset();
+
+	if(table_base==0)
+		return;
+
+	// find the section with the data table
+	EXEIO::section *pSec=find_section(table_base,elfiop);
+	if(!pSec)
+		return;
+
+	auto table_max=numeric_limits<uint32_t>::max();
+	auto cmp_insn=(Instruction_t*)nullptr;
+	if(backup_until("cmp ", cmp_insn, insn))
+	{
+		assert(cmp_insn);
+		const auto cmp_decode=DecodedInstruction_t::factory(cmp_insn);
+		table_max=cmp_decode->getImmediate();
+	}
+	
+
+	// if the section has no data, abort 
+	const char* secdata=pSec->get_data();
+	if(!secdata)
+		return;
+
+	// get the base offset into the section
+	VirtualOffset_t offset=table_base-pSec->get_address();
+
+
+	// check to see if stars already marked this complete.
+	// if so, just figure out the table size
+	if(jmptables[insn].getAnalysisStatus()==iasAnalysisComplete)
+	{
+		// we already know it's a type3, we can just record the type and table base.
+		jmptables[insn].AddSwitchType(prov);
+		jmptables[insn].SetTableStart(table_base);
+
+		// try to determine the table size using the complete set of targets.
+		int i=0;
+		for(i=0;true;i++)
+		{
+			
+			if((int)(offset+i*ptrsize+ptrsize) > (int)pSec->get_size())
+				return;
+
+			const void *table_entry_ptr=(const int*)&(secdata[offset+i*ptrsize]);
+
+			VirtualOffset_t table_entry=0;
+			switch(ptrsize)
+			{
+				case 4:
+					table_entry=(VirtualOffset_t)*(int*)table_entry_ptr;
+					break;
+				case 8:
+					table_entry=(VirtualOffset_t)*(int**)table_entry_ptr;
+					break;
+				default:
+					assert(0);
+			}
+
+			Instruction_t* ibt=lookupInstruction(firp,table_entry);
+			// if we didn't find an instruction or the insn isn't in our set, stop looking, we've found the table size
+			if(ibt==nullptr || jmptables[insn].find(ibt) == jmptables[insn].end())
+				break;
+		}
+		jmptables[insn].SetTableSize(i);
+		if(getenv("IB_VERBOSE"))
+		{
+			cout<<"Found type3 at "<<hex<<insn->getAddress()->getVirtualOffset()
+			    <<" already complete, setting base to "<<hex<<table_base<<" and size to "<<dec<<i<<endl;
+		}
+		return;
+	}
+	
+
+	auto i=0U;
+	for(i=0;i<3;i++)
+	{
+		if((int)(offset+i*ptrsize+ptrsize) > (int)pSec->get_size())
+			return;
+
+		const void *table_entry_ptr=(const int*)&(secdata[offset+i*ptrsize]);
+
+		VirtualOffset_t table_entry=0;
+		switch(ptrsize)
+		{
+			case 4:
+				table_entry=(VirtualOffset_t)*(int*)table_entry_ptr;
+				break;
+			case 8:
+				table_entry=(VirtualOffset_t)*(int**)table_entry_ptr;
+				break;
+			default:
+				assert(0);
+		}
+
+		if(getenv("IB_VERBOSE")!=0)
+			cout<<"Checking target base:" << std::hex << table_entry << ", " << table_base+i*ptrsize<<endl;
+
+		/* if there's no base register and no index reg, */
+		/* then this jmp can't have more than one valid table entry */
+		if( !disasm.getOperand(0)->hasBaseRegister() && !disasm.getOperand(0)->hasIndexRegister()) 
+		{
+			/* but the table can have 1 valid entry. */
+			if(pSec->get_name()==".got.plt")
+			{	
+	                        Instruction_t *ibtarget = lookupInstruction(firp, table_entry);
+				if(ibtarget)
+				{
+					jmptables[I5].insert(ibtarget);
+					jmptables[I5].setAnalysisStatus(iasAnalysisModuleComplete);
+					possible_target(table_entry,table_base+0*ptrsize, ibt_provenance_t::ibtp_gotplt);
+					if(getenv("IB_VERBOSE")!=0)
+						cout<<hex<<"Found  plt dispatch ("<<disasm.getDisassembly()<<"') at "<<I5->getAddress()->getVirtualOffset()<< endl;
+					return;
+				}
+			}
+			if(pSec->isWriteable())
+				possible_target(table_entry,table_base+0*ptrsize, ibt_provenance_t::ibtp_data);
+			else
+				possible_target(table_entry,table_base+0*ptrsize, ibt_provenance_t::ibtp_rodata);
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<hex<<"Found  constant-memory dispatch from non- .got.plt location ("<<disasm.getDisassembly()<<"') at "
+				    <<I5->getAddress()->getVirtualOffset()<< endl;
+			return;
+		}
+		if(!is_possible_target(table_entry,table_base+i*ptrsize))
+		{
+			if(getenv("IB_VERBOSE")!=0)
+			{
+				cout<<hex<<"Found (type3) candidate for switch dispatch for '"<<disasm.getDisassembly()<<"' at "
+				    <<I5->getAddress()->getVirtualOffset()<< " with table_base="<<table_base<<endl;
+				cout<<"Found table_entry "<<hex<<table_entry<<" is not valid\n"<<endl;
+			}
+			return;	
+		}
+	}
+
+
+	cout<<hex<<"Definitely found (type3) switch dispatch at "<<I5->getAddress()->getVirtualOffset()<< " with table_base="<<table_base<<endl;
+
+	/* did we finish the loop or break out? */
+	if(i==3)
+	{
+		if(getenv("IB_VERBOSE")!=0)
+			cout<<"Found switch table (type3)  at "<<hex<<table_base<<endl;
+		jmptables[insn].AddSwitchType(prov);
+		jmptables[insn].SetTableStart(table_base);
+		// finished the loop.
+		for(i=0;true;i++)
+		{
+			if(i>table_max)
+			{
+				if(getenv("IB_VERBOSE")!=0)
+				{
+					cout<<hex<<"Switch dispatch at "<<I5->getAddress()->getVirtualOffset()<< " with table_base="
+					    <<table_base<<" is complete!"<<endl;
+				}
+				jmptables[insn].setAnalysisStatus(iasAnalysisComplete);
+			}
+			if((int)(offset+i*ptrsize+ptrsize) > (int)pSec->get_size() || i > table_max)
+				return;
+
+			const void *table_entry_ptr=(const int*)&(secdata[offset+i*ptrsize]);
+
+			VirtualOffset_t table_entry=0;
+			switch(ptrsize)
+			{
+				case 4:
+					table_entry=(VirtualOffset_t)*(int*)table_entry_ptr;
+					break;
+				case 8:
+					table_entry=(VirtualOffset_t)*(int**)table_entry_ptr;
+					break;
+				default:
+					assert(0);
+			}
+
+			Instruction_t* ibt=lookupInstruction(firp,table_entry);
+			if(!possible_target(table_entry,table_base+i*ptrsize,prov) || ibt==nullptr)
+				return;
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"Found switch table (thunk-relative) entry["<<dec<<i<<"], "<<hex<<table_entry<<endl;
+
+			// make table bigger.
+			jmptables[insn].SetTableSize(i+1);/* 0 index, and this index is determined valid. */
+			jmptables[insn].insert(ibt);
+		}
+	}
+	else
+	{
+		if(getenv("IB_VERBOSE")!=0)
+			cout<<"Found that  "<<hex<<table_base<<endl;
+	}
+}
+
+
+
+/* check if this instruction is an indirect jump via a register,
+ * if so, see if we can trace back a few instructions to find a
+ * the start of the table.
+ */
+void check_for_PIC_switch_table64(FileIR_t* firp, Instruction_t* insn, const DecodedInstruction_t& p_disasm, EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type4;
+/* here's the pattern we're looking for */
+#if 0
+I1:   0x000000000044425a <+218>:        cmp    DWORD PTR [rax+0x8],0xd   // bounds checking code, 0xd cases. switch(i) has i stored in [rax+8] in this e.g.
+I2:   0x000000000044425e <+222>:        jbe    0x444320 <_gedit_tab_get_icon+416>
+<new bb>
+I3:   0x0000000000444264 <+228>:        mov    rdi,rbp // default case, also jumped to via indirect branch below
+<snip (doesnt fall through)>
+I4:   0x0000000000444320 <+416>:        mov    edx,DWORD PTR [rax+0x8]		# load from memory into index reg EDX.
+
+THIS ONE
+I5:   0x0000000000444323 <+419>:        lea    rax,[rip+0x3e1b6]        # 0x4824e0
+I6:   0x000000000044432a <+426>:        movsxd rdx,DWORD PTR [rax+rdx*4]
+I7:   0x000000000044432e <+430>:        add    rax,rdx  // OR: lea rax, [rdx+rax]
+I8:   0x0000000000444331 <+433>:        jmp    rax      // relatively standard switch dispatch code
+
+
+D1:   0x4824e0: .long 0x4824e0-L1       // L1-LN are labels in the code where case statements start.
+D2:   0x4824e4: .long 0x4824e0-L2
+..
+DN:   0x4824XX: .long 0x4824e0-LN
+
+
+
+
+Alternate version:
+
+   	0x00000000000b939d <+25>:	cmp    DWORD PTR [rbp-0x4],0xf
+   	0x00000000000b93a1 <+29>:	ja     0xb94a1 <worker_query+285>
+   	0x00000000000b93a7 <+35>:	mov    eax,DWORD PTR [rbp-0x4]
+   	0x00000000000b93aa <+38>:	lea    rdx,[rax*4+0x0]
+I5-1   	0x00000000000b93b2 <+46>:	lea    rax,[rip+0x1f347]        # 0xd8700
+I6-2    0x00000000000b93b9 <+53>:	mov    eax,DWORD PTR [rdx+rax*1] 
+I6      0x00000000000b93bc <+56>:	movsxd rdx,eax
+I5-2   	0x00000000000b93bf <+59>:	lea    rax,[rip+0x1f33a]        # 0xd8700
+   	0x00000000000b93c6 <+66>:	add    rax,rdx
+   	0x00000000000b93c9 <+69>:	jmp    rax
+
+Note: Since I6 doesnt access memory, do another backup until with to verify address format 
+
+Alternate version 2:
+
+	   0xdcf7 <+7>:	mov    r8,QWORD PTR [rdi+0xa0]
+	   0xdcfe <+14>:	cmp    r8,rax
+	   0xdd01 <+17>:	jbe    0xdd5c <httpd_got_request+108>
+	   0xdd03 <+19>:	mov    r9,QWORD PTR [rdi+0x90]
+I5	   0xdd0a <+26>:	lea    rcx,[rip+0x2a427]        # 0x38138
+	   0xdd11 <+33>:	cmp    DWORD PTR [rdi+0xb0],0xb
+	   0xdd18 <+40>:	movzx  edx,BYTE PTR [r9+rax*1]
+	   0xdd1d <+45>:	ja     0xdd4c <httpd_got_request+92>
+	   0xdd1f <+47>:	mov    esi,DWORD PTR [rdi+0xb0]
+I6	   0xdd25 <+53>:	movsxd rsi,DWORD PTR [rcx+rsi*4]
+I7	   0xdd29 <+57>:	add    rsi,rcx
+I8	   0xdd2c <+60>:	jmp    rsi
+
+Note: Here the operands of the add are reversed, so lookup code was not finding I5 where it was expected.c
+
+
+#endif
+
+
+	// for now, only trying to find I4-I8.  ideally finding I1 would let us know the size of the
+	// jump table.  We'll figure out N by trying targets until they fail to produce something valid.
+
+	string table_index_str;
+	Instruction_t* I8=insn;
+	Instruction_t* I7=nullptr;
+	Instruction_t* I6=nullptr;
+	Instruction_t* I5=nullptr;
+	Instruction_t* I1=nullptr;
+	// check if I8 is a jump
+	if(strstr(p_disasm.getMnemonic().c_str(), "jmp")==nullptr)
+		return;
+
+	// return if it's a jump to a constant address, these are common
+	if(p_disasm.getOperand(0)->isConstant()) 
+		return;
+	// return if it's a jump to a memory address
+	if(p_disasm.getOperand(0)->isMemory()) 
+		return;
+
+	// has to be a jump to a register now
+
+	/* 
+	 * This is the instruction that adds the table value
+	 * to the base address of the table. The result is 
+	 * the target address of the jump.
+	 *
+	 * Backup and find the instruction that's an add or lea before I8.
+	 */
+	table_index_str = "(add ";
+	table_index_str += p_disasm.getOperand(0)->getString(); 
+	table_index_str += "|lea ";
+	table_index_str += p_disasm.getOperand(0)->getString(); 
+	table_index_str += ")";
+
+	const auto cmp_str = string("cmp ") + p_disasm.getOperand(0)->getString(); 
+
+	// this was completely broken because argument2 had a null mnemonic, which we found out because getOperand(1) threw an exception.
+	// i suspect it's attempting to find a compare of operand1 on the RHS of a compare, but i need better regex foo to get that.
+	// for now, repeat what was working.
+	const auto cmp_str2 = string("cmp "); 
+
+	if(!backup_until(table_index_str.c_str(), I7, I8))
+		return;
+
+	const auto d7=DecodedInstruction_t::factory(I7);
+
+	// Check if lea instruction is being used as add (scale=1, disp=0)
+	if(strstr(d7->getMnemonic().c_str(), "lea"))
+	{
+		if(!(d7->getOperand(1)->isMemory() ))
+			return;
+		if(!(d7->getOperand(1)->getScaleValue() == 1 && d7->getOperand(1)->getMemoryDisplacement() == 0))
+			return;
+	} 
+	// backup and find the instruction that's an movsxd before I7
+	/*
+	 * This instruction will contain the register names for
+	 * the index and the address of the base of the table
+	 */
+	if(!backup_until("movsxd", I6, I7))
+		return;
+
+	string lea_string="lea ";
+	
+	const auto d6=DecodedInstruction_t::factory(I6);
+	if( d6->getOperand(1)->isMemory() )
+	{
+		// try to be smarter for memory types.
+
+		// 64-bit register names are OK here, because this pattern already won't apply to 32-bit code.
+		/*
+		 * base_reg is the register that holds the address
+		 * for the base of the jump table.
+		 */
+		string base_reg="";
+		if(!d6->getOperand(1)->hasBaseRegister() )
+			return;
+		switch(d6->getOperand(1)->getBaseRegister() )
+		{
+			case 0/*REG0*/: base_reg="rax"; break;
+			case 1/*REG1*/: base_reg="rcx"; break;
+			case 2/*REG2*/: base_reg="rdx"; break;
+			case 3/*REG3*/: base_reg="rbx"; break;
+			case 4/*REG4*/: base_reg="rsp"; break;
+			case 5/*REG5*/: base_reg="rbp"; break;
+			case 6/*REG6*/: base_reg="rsi"; break;
+			case 7/*REG7*/: base_reg="rdi"; break;
+			case 8/*REG8*/: base_reg="r8"; break;
+			case 9/*REG9*/: base_reg="r9"; break;
+			case 10/*REG10*/: base_reg="r10"; break;
+			case 11/*REG11*/: base_reg="r11"; break;
+			case 12/*REG12*/: base_reg="r12"; break;
+			case 13/*REG13*/: base_reg="r13"; break;
+			case 14/*REG14*/: base_reg="r14"; break;
+			case 15/*REG15*/: base_reg="r15"; break;
+			default: 
+				// no base register;
+				return;
+		}
+		lea_string+=base_reg;
+	}	
+
+	/* 
+	 * This is the instruction that loads the address of the base
+	 * of the table into a register.
+	 *
+	 * backup and find the instruction that's an lea before I6;
+	 * make sure we match the register,
+	 * and allow recursion in the search (last parameter as true).
+	 *
+	 */
+
+	 /*
+	  * Convert to return set
+		*/
+
+	auto found_leas=InstructionSet_t();
+	
+	
+	if (I6->getFunction())
+	{
+		cout << "Using find_in_function method." << endl;
+		found_leas=find_in_function(lea_string,I6->getFunction());
+	}
+	else
+	{
+		cout << "Using fallback method." << endl;
+		if (backup_until(lea_string.c_str(), I5, I6, "", true))
+		{
+			found_leas.insert(I5);
+		}
+	}
+	if (found_leas.empty())
+	{
+		/*
+		 * TODO: Write this to warning.txt
+		 */
+		cout << "WARNING: No I5 candidates found!" << endl;
+	}
+
+	/*
+	 * Check each one that is returned.
+	 */
+	auto found_leas_it = found_leas.begin();
+	for (; found_leas_it != found_leas.end(); found_leas_it++) 
+	{
+		auto I5_cur = *found_leas_it;
+		auto d5p=DecodedInstruction_t::factory(I5_cur);
+		auto &d5=*d5p;
+
+		if(!(d5.getOperand(1)->isMemory() ))
+			continue;
+		if(!(d5.getOperand(1)->isPcrel() ))
+			continue;
+
+		// note that we'd normally have to add the displacement to the
+		// instruction address (and include the instruction's size, etc.
+		// but, fix_calls has already removed this oddity so we can relocate
+		// the instruction.
+		VirtualOffset_t D1=strtol(d5.getOperand(1)->getString().c_str(), nullptr, 0);
+		D1+=I5_cur->getAddress()->getVirtualOffset();
+
+		// find the section with the data table
+		auto pSec=find_section(D1,elfiop);
+
+		// sanity check there's a section
+		if(!pSec)
+			continue;
+
+		const char* secdata=pSec->get_data();
+
+		// if the section has no data, abort 
+		if(!secdata)
+			continue;
+
+		auto table_size = 0U;
+		if(backup_until(cmp_str.c_str(), I1, I8))
+		{
+			auto d1=DecodedInstruction_t::factory(I1);
+			table_size = d1->getImmediate(); // Instruction.Immediat;
+			if (table_size <= 4)
+			{
+				cout<<"pic64: found I1 ('"<<d1->getDisassembly()<<"'), but could not find size of switch table"<<endl;
+				// set table_size to be very large, so we can still do pinning appropriately
+				table_size=std::numeric_limits<int>::max();
+			}
+		}
+		else if(backup_until(cmp_str2.c_str(), I1, I8))
+		{
+			auto d1=DecodedInstruction_t::factory(I1);
+			table_size = d1->getImmediate()/*Instruction.Immediat*/;
+			if (table_size <= 4)
+			{
+				// set table_size to be very large, so we can still do pinning appropriately
+				cout<<"pic64: found I1 ('"<<d1->getDisassembly()<<"'), but could not find size of switch table"<<endl;
+				table_size=std::numeric_limits<int>::max();
+			}
+		}
+		else
+		{
+			cout<<"pic64: could not find size of switch table"<<endl;
+
+			// we set the table_size variable to max_int so that we can still do pinning, 
+			// but we won't do the switch identification.
+			table_size=std::numeric_limits<int>::max();
+		}
+
+		auto ibtargets=InstructionSet_t();
+		auto offset=D1-pSec->get_address();
+		auto entry=0U;
+		auto found_table_error = false;
+		do
+		{
+			// check that we can still grab a word from this section
+			if((int)(offset+sizeof(int)) > (int)pSec->get_size())
+			{
+				found_table_error = true;
+				break;
+			}
+
+			const int *table_entry_ptr=(const int*)&(secdata[offset]);
+			VirtualOffset_t table_entry=*table_entry_ptr;
+
+			if(!possible_target(D1+table_entry, 0/* from addr unknown */,prov))
+			{
+				found_table_error = true;
+				break;
+			}
+
+			if(getenv("IB_VERBOSE"))
+			{
+				cout<<"Found possible table entry, at: "<< std::hex << I8->getAddress()->getVirtualOffset()
+			    		<< " insn: " << d5.getDisassembly()<< " d1: "
+			    		<< D1 << " table_entry:" << table_entry 
+			    		<< " target: "<< D1+table_entry << std::dec << endl;
+			}
+
+			auto ibtarget = lookupInstruction(firp, D1+table_entry);
+			if (ibtarget && ibtargets.size() <= table_size)
+			{
+				if(getenv("IB_VERBOSE"))
+					cout << "jmp table [" << entry << "]: " << hex << table_entry << dec << endl;
+				ibtargets.insert(ibtarget);
+			}
+			else
+			{
+				if(getenv("IB_VERBOSE"))
+					cout << "      INVALID target" << endl;
+
+				found_table_error = true;
+				break;
+			}
+			offset+=sizeof(int);
+			entry++;
+		} while ( entry<=table_size);
+
+		
+		// valid switch table? may or may not have default: in the switch
+		// table size = 8, #entries: 9 b/c of default
+		cout << "pic64: detected table size (max_int means no found): 0x"<< hex << table_size << " #entries: 0x" << entry << " ibtargets.size: " << ibtargets.size() << endl;
+
+		jmptables[I8].addTargets(ibtargets);
+		// note that there may be an off-by-one error here as table size depends on whether instruction I2 is a jb or jbe.
+		if (!found_table_error)
+		{
+			cout << "pic64: valid switch table for "<<hex<<I8->getAddress()->getVirtualOffset()
+			     <<"detected ibtp_switchtable_type4" << endl;
+			jmptables[I8].setAnalysisStatus(iasAnalysisComplete);
+		}
+		else
+		{
+			cout << "pic64: INVALID switch table detected for, "
+			     <<hex<<I8->getAddress()->getVirtualOffset()<<"type=ibtp_switchtable_type4" << endl;
+		}
+	}
+}
+
+/*
+  switch table pattern (non-PIC):
+      40062a:	8d 40 ec             	lea  eax,[rax-0x14]
+  I1: 40062d:	83 f8 08             	cmp  eax,0x8                     'size
+  I2: 400630:	0f 87 98 00 00 00    	ja   4006ce <main+0xbb>
+      400636:	89 c0                	mov  eax,eax
+  I3: 400638:	ff 24 c5 10 08 40 00	jmp  QWORD PTR [rax*8+0x400810]  'branch
+      40063f:	bf a9 07 40 00       	mov  edi,0x4007a9
+      400644:	e8 67 fe ff ff       	call 4004b0 <puts@plt>
+      400649:	e9 96 00 00 00       	jmp  4006e4 <main+0xd1>
+
+	nb: handles both 32 and 64 bit
+*/
+void check_for_nonPIC_switch_table_pattern2(FileIR_t* firp, Instruction_t* insn, const DecodedInstruction_t& p_disasm, EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type5;
+	Instruction_t *I1 = nullptr;
+	Instruction_t *IJ = insn;
+
+	assert(IJ);
+
+	// check if IJ is a jump
+	if(strstr(p_disasm.getMnemonic().c_str(), "jmp")==nullptr)
+		return;
+
+	// look for a memory type
+	if(!(p_disasm.getOperand(0)->isMemory()))
+		return;
+
+	// make sure there's a scaling factor
+	if (!p_disasm.getOperand(0)->hasIndexRegister() || p_disasm.getOperand(0)->getScaleValue() < 4)
+		return;
+
+	// extract start of jmp table
+	VirtualOffset_t table_offset = p_disasm.getAddress(); // disasm.Instruction.AddrValue;
+	if(table_offset==0)
+		return;
+
+	cout<<hex<<"(nonPIC-pattern2): Found switch dispatch at 0x"<<hex<<IJ->getAddress()->getVirtualOffset()<< " with table_offset="<<hex<<table_offset<<dec<<endl;
+
+	if(!backup_until("cmp", I1, IJ))
+	{
+		cout<<"(nonPIC): could not find size of switch table"<<endl;
+		return;
+	}
+
+	// extract size off the comparison
+	// make sure not off by one
+	auto d1p=DecodedInstruction_t::factory(I1);
+	auto &d1=*d1p;
+	VirtualOffset_t table_size = d1.getImmediate()/*d1.Instruction.Immediat*/;
+
+	if (table_size <= 0) return;
+
+	cout<<"(nonPIC-pattern2): size of jmp table: "<< table_size << endl;
+
+	// find the section with the data table
+    	auto pSec=find_section(table_offset,elfiop);
+	if(!pSec)
+	{
+		return;
+	}
+
+	// if the section has no data, abort 
+	const char* secdata=pSec->get_data();
+	if(!secdata)
+		return;
+
+	// get the base offset into the section
+    	auto offset=table_offset-pSec->get_address();
+	auto i=0U;
+
+	InstructionSet_t ibtargets;
+	for(i=0;i<table_size;++i)
+	{
+		if((int)(offset+i*arch_ptr_bytes()+sizeof(int)) > (int)pSec->get_size())
+		{
+			cout << "jmp table outside of section range ==> invalid switch table" << endl;
+			return;
+		}
+
+		const VirtualOffset_t *table_entry_ptr=(const VirtualOffset_t*)&(secdata[offset+i*arch_ptr_bytes()]);
+		VirtualOffset_t table_entry=*table_entry_ptr;
+		possible_target(table_entry,0,prov);
+
+		Instruction_t *ibtarget = lookupInstruction(firp, table_entry);
+		if (!ibtarget) {
+			if(getenv("IB_VERBOSE"))
+				cout << "0x" << hex << table_entry << " is not an instruction, invalid switch table" << endl;
+			return;
+		}
+
+		if(getenv("IB_VERBOSE"))
+			cout << "jmp table [" << i << "]: " << hex << table_entry << dec << endl;
+		ibtargets.insert(ibtarget);
+	}
+
+	cout << "(non-PIC) valid switch table found - ibtp_switchtable_type5" << endl;
+
+	jmptables[IJ].addTargets(ibtargets);
+	jmptables[IJ].setAnalysisStatus(iasAnalysisComplete);
+}
+
+/*
+  Handles the following switch table pattern:
+  I1: 400518:   83 7d ec 0c             cmpl   $0xc,-0x14(%rbp)          'size
+  I2: 40051c:   0f 87 b7 00 00 00       ja     4005d9 <main+0xe5>        
+  I3: 400522:   8b 45 ec                mov    -0x14(%rbp),%eax 
+  I4: 400525:   48 8b 04 c5 20 07 40    mov    0x400720(,%rax,8),%rax    'start jump table
+      40052c:   00  
+  IJ: 40052d:   ff e0                   jmpq   *%rax                     'indirect branch
+      40052f:   c7 45 f4 00 00 00 00    movl   $0x0,-0xc(%rbp)
+      400536:   c7 45 f8 03 00 00 00    movl   $0x3,-0x8(%rbp)
+
+	nb: handles both 32 and 64 bit
+*/
+void check_for_nonPIC_switch_table(FileIR_t* firp, Instruction_t* insn, const DecodedInstruction_t& p_disasm, EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type6;
+	Instruction_t *I1 = nullptr;
+	Instruction_t *I4 = nullptr;
+	Instruction_t *IJ = insn;
+
+	if (!IJ) return;
+
+	// check if IJ is a jump
+	if(strstr(p_disasm.getMnemonic().c_str()/*disasm.Instruction.Mnemonic*/, "jmp")==nullptr)
+		return;
+
+	// return if it's a jump to a constant address, these are common
+	if(p_disasm.getOperand(0)->isConstant() /*disasm.Argument1.ArgType&CONSTANT_TYPE*/)
+		return;
+
+	// return if it's a jump to a memory address
+	if(p_disasm.getOperand(0)->isMemory() /*disasm.Argument1.ArgType&MEMORY_TYPE*/)
+		return;
+
+	// has to be a jump to a register now
+
+	// backup and find the instruction that's a mov
+	if(!backup_until("mov", I4, IJ))
+		return;
+
+	// extract start of jmp table
+	// DISASM d4;
+	// Disassemble(I4,d4);
+	auto d4p=DecodedInstruction_t::factory(I4);
+	auto &d4=*d4p;
+
+	// make sure there's a scaling factor
+	if (d4.getOperand(1)->isMemory() && d4.getOperand(1)->getScaleValue() < 4)
+		return;
+
+	VirtualOffset_t table_offset=d4.getAddress(); 
+	if(table_offset==0)
+		return;
+
+	if(getenv("IB_VERBOSE"))
+		cout<<hex<<"(nonPIC): Found switch dispatch at 0x"<<hex<<I4->getAddress()->getVirtualOffset()<< " with table_offset="<<hex<<table_offset<<dec<<endl;
+
+	if(!backup_until("cmp", I1, I4))
+	{
+		cout<<"(nonPIC): could not find size of switch table"<<endl;
+		return;
+	}
+
+	// extract size off the comparison
+	// make sure not off by one
+	auto d1p=DecodedInstruction_t::factory(I1);
+	auto &d1=*d1p;
+	auto table_size = d1.getImmediate(); // d1.Instruction.Immediat;
+	if (table_size <= 0) return;
+
+	if(getenv("IB_VERBOSE"))
+		cout<<"(nonPIC): size of jmp table: "<< table_size << endl;
+
+	// find the section with the data table
+	auto pSec=find_section(table_offset,elfiop);
+	if(!pSec)
+	{
+		cout<<hex<<"(nonPIC): could not find jump table in section"<<endl;
+		return;
+	}
+
+	// if the section has no data, abort 
+	const char* secdata=pSec->get_data();
+	if(!secdata)
+		return;
+
+	// get the base offset into the section
+	auto offset=table_offset-pSec->get_address();
+	auto i=0U;
+
+	if(getenv("IB_VERBOSE"))
+		cout << hex << "offset: " << offset << " arch bit width: " << dec << firp->getArchitectureBitWidth() << endl;
+
+	InstructionSet_t ibtargets;
+	for(i=0;i<table_size;++i)
+	{
+		if((int)(offset+i*arch_ptr_bytes()+sizeof(int)) > (int)pSec->get_size())
+		{
+			cout << "jmp table outside of section range ==> invalid switch table" << endl;
+			return;
+		}
+
+		VirtualOffset_t table_entry=0;
+		if (firp->getArchitectureBitWidth()==32)
+		{
+			const int *table_entry_ptr=(const int*)&(secdata[offset+i*arch_ptr_bytes()]);
+			table_entry=*table_entry_ptr;
+		}
+		else if (firp->getArchitectureBitWidth()==64)
+		{
+			const VirtualOffset_t *table_entry_ptr=(const VirtualOffset_t*)&(secdata[offset+i*arch_ptr_bytes()]);
+			table_entry=*table_entry_ptr;
+		}
+		else 
+			assert(0 && "Unknown arch size.");
+
+		possible_target(table_entry, 0 /* from addr unknown */, prov);
+		auto ibtarget = lookupInstruction(firp, table_entry);
+		if (!ibtarget) {
+			if(getenv("IB_VERBOSE"))
+				cout << "0x" << hex << table_entry << " is not an instruction, invalid switch table" << endl;
+			return;
+		}
+
+		if(getenv("IB_VERBOSE"))
+			cout << "jmp table [" << i << "]: " << hex << table_entry << dec << endl;
+		ibtargets.insert(ibtarget);
+	}
+
+	cout << "(non-PIC) valid switch table found - prov=ibt_provenance_t::ibtp_switchtable_type6" << endl;
+	jmptables[IJ].addTargets(ibtargets);
+	jmptables[IJ].setAnalysisStatus(iasAnalysisComplete);
+}
+
+void calc_preds(FileIR_t* firp)
+{
+        preds.clear();
+        for(auto insn : firp->getInstructions())
+        {
+                if(insn->getTarget())
+                        preds[insn->getTarget()].insert(insn);
+                if(insn->getFallthrough())
+                        preds[insn->getFallthrough()].insert(insn);
+        }
+}
+
+void handle_takes_address_annot(FileIR_t* firp,Instruction_t* insn, MEDS_TakesAddressAnnotation* p_takes_address_annotation)
+{
+	const auto referenced_addr=p_takes_address_annotation->GetReferencedAddress();
+	if(p_takes_address_annotation->isCode())
+	{
+		const auto refd_addr=referenced_addr;
+		possible_target(refd_addr,insn->getAddress()->getVirtualOffset(), ibt_provenance_t::ibtp_text);
+	}
+	else
+	{
+		all_add_adrp_results[insn->getFunction()].insert(referenced_addr);
+	}
+}
+
+void handle_ib_annot(FileIR_t* firp,Instruction_t* insn, MEDS_IBAnnotation* p_ib_annotation)
+{
+	if(p_ib_annotation->IsComplete())
+	{
+		jmptables[insn].setAnalysisStatus(iasAnalysisComplete);
+	}
+}
+void handle_ibt_annot(FileIR_t* firp,Instruction_t* insn, MEDS_IBTAnnotation* p_ibt_annotation)
+{
+/*
+ * ibt_prov reason codes
+ *              static const provtype_t ibtp_stars_ret=1<<11;
+ *              static const provtype_t ibtp_stars_switch=1<<12;
+ *              static const provtype_t ibtp_stars_data=1<<13;
+ *              static const provtype_t ibtp_stars_unknown=1<<14;
+ *              static const provtype_t ibtp_stars_addressed=1<<15;
+ *              static const provtype_t ibtp_stars_unreachable=1<<15;
+ */
+/* meds annotations
+ *                typedef enum { SWITCH, RET, DATA, UNREACHABLE, ADDRESSED, UNKNOWN } ibt_reason_code_t;
+ */
+	//cout<<"at handl_ibt with addr="<<hex<<insn->getAddress()->getVirtualOffset()<<" code="<<p_ibt_annotation->GetReason()<<endl;
+	switch(p_ibt_annotation->GetReason())
+	{
+		case MEDS_IBTAnnotation::SWITCH:
+		case MEDS_IBTAnnotation::INDIRCALL:
+		{
+			possible_target((VirtualOffset_t)p_ibt_annotation->getVirtualOffset().getOffset(),
+				0,ibt_provenance_t::ibtp_stars_switch);
+			auto addr=(VirtualOffset_t)p_ibt_annotation->GetXrefAddr();
+			auto fromib=lookupInstruction(firp, addr);
+			auto ibt=lookupInstruction(firp, p_ibt_annotation->getVirtualOffset().getOffset());
+			if(fromib && ibt)
+			{
+				if(getenv("IB_VERBOSE")!=nullptr)
+					cout<<hex<<"Adding call/switch icfs: "<<fromib->getAddress()->getVirtualOffset()<<"->"<<ibt->getAddress()->getVirtualOffset()<<endl;
+				jmptables[fromib].insert(ibt);
+			}
+			else
+			{
+				cout<<"Warning:  cannot find source or dest for call/switch icfs."<<endl;
+			}
+			break;
+		}
+		case MEDS_IBTAnnotation::RET:
+		{
+			/* we are not going to mark return points as IBTs yet.  that's fix-calls job */
+			// possible_target((VirtualOffset_t)p_ibt_annotation->getVirtualOffset().getOffset(),
+			// 	0,ibt_provenance_t::ibtp_stars_ret);
+
+
+			auto fromaddr=(VirtualOffset_t)p_ibt_annotation->GetXrefAddr();
+			auto fromib=lookupInstruction(firp, fromaddr);
+			auto toaddr=p_ibt_annotation->getVirtualOffset().getOffset();
+			auto ibt=lookupInstruction(firp, toaddr);
+			if(fromib && ibt)
+			{
+				if(getenv("IB_VERBOSE")!=nullptr)
+					cout<<hex<<"Adding ret icfs: "<<fromib->getAddress()->getVirtualOffset()<<"->"<<ibt->getAddress()->getVirtualOffset()<<endl;
+				jmptables[fromib].insert(ibt);
+			}
+			else
+			{
+				cout<<"Warning:  cannot find source ("<<hex<<fromaddr<<") or dest ("<<hex<<toaddr<<") for ret icfs."<<endl;
+			}
+			break;
+		}
+		case MEDS_IBTAnnotation::DATA:
+		{
+			possible_target((VirtualOffset_t)p_ibt_annotation->getVirtualOffset().getOffset(),
+				0,ibt_provenance_t::ibtp_stars_data);
+			if(getenv("IB_VERBOSE")!=nullptr)
+				cout<<hex<<"detected stars data ibt at"<<p_ibt_annotation->getVirtualOffset().getOffset()<<endl;
+			break;
+		}
+		case MEDS_IBTAnnotation::UNREACHABLE:
+		{
+			possible_target((VirtualOffset_t)p_ibt_annotation->getVirtualOffset().getOffset(),
+				0,ibt_provenance_t::ibtp_stars_unreachable);
+			if(getenv("IB_VERBOSE")!=nullptr)
+				cout<<hex<<"detected stars unreachable ibt at"<<p_ibt_annotation->getVirtualOffset().getOffset()<<endl;
+			break;
+		}
+		case MEDS_IBTAnnotation::ADDRESSED:
+		{
+			possible_target((VirtualOffset_t)p_ibt_annotation->getVirtualOffset().getOffset(),
+				0,ibt_provenance_t::ibtp_stars_addressed);
+			if(getenv("IB_VERBOSE")!=nullptr)
+				cout<<hex<<"detected stars addresssed ibt at"<<p_ibt_annotation->getVirtualOffset().getOffset()<<endl;
+			break;
+		}
+		case MEDS_IBTAnnotation::UNKNOWN:
+		{
+			possible_target((VirtualOffset_t)p_ibt_annotation->getVirtualOffset().getOffset(),
+				0,ibt_provenance_t::ibtp_stars_unknown);
+			if(getenv("IB_VERBOSE")!=nullptr)
+				cout<<hex<<"detected stars unknown ibt at"<<p_ibt_annotation->getVirtualOffset().getOffset()<<endl;
+			break;
+		}
+		default:
+		{
+			assert(0); // unexpected ibt annotation.
+		}
+	}
+
+
+}
+
+void read_stars_xref_file(FileIR_t* firp)
+{
+
+	const auto BINARY_NAME=string("a.ncexe");
+	const auto SHARED_OBJECTS_DIR=string("shared_objects");
+
+	const auto fileBasename = string(basename((char*)firp->getFile()->getURL().c_str()));
+
+	auto annotationParser=MEDS_AnnotationParser();
+	// need to map filename to integer annotation file produced by STARS
+	// this should be retrieved from the IRDB but for now, we use files to store annotations
+	// convention from within the peasoup subdirectory is:
+	//      a.ncexe.infoannot
+	//      shared_objects/<shared-lib-filename>.infoannot
+	const auto annotationFilename =(fileBasename==BINARY_NAME) ? BINARY_NAME : SHARED_OBJECTS_DIR + "/" + fileBasename ;
+
+	try
+	{
+		annotationParser.parseFile(annotationFilename+".STARSxrefs");
+	}
+	catch (const string &s)
+	{
+		cout<<"Warning:  annotation parser reports error: "<<s<<endl;
+	}
+
+        for(auto insn : firp->getInstructions())
+	{
+		const auto irdb_vo = insn->getAddress()->getVirtualOffset();
+		const auto vo=VirtualOffset_t(irdb_vo);
+
+		/* find it in the annotations */
+		const auto ret = annotationParser.getAnnotations().equal_range(vo);
+
+		/* for each annotation for this instruction */
+		for (auto ait = ret.first; ait != ret.second; ++ait)
+		{
+			/* is this annotation a funcSafe annotation? */
+			const auto p_ib_annotation=dynamic_cast<MEDS_IBAnnotation*>(ait->second);
+			const auto p_ibt_annotation=dynamic_cast<MEDS_IBTAnnotation*>(ait->second);
+			const auto p_takes_address_annotation=dynamic_cast<MEDS_TakesAddressAnnotation*>(ait->second);
+			if(p_ib_annotation && p_ib_annotation->isValid())
+				handle_ib_annot(firp,insn,p_ib_annotation);
+			else if(p_ibt_annotation && p_ibt_annotation->isValid())
+				handle_ibt_annot(firp,insn,p_ibt_annotation);
+			else if(p_takes_address_annotation && p_takes_address_annotation->isValid())
+				handle_takes_address_annot(firp,insn,p_takes_address_annotation);
+		}
+	}
+}
+
+void process_dynsym(FileIR_t* firp)
+{
+	auto dynsymfile = popen("$PS_OBJDUMP -T readeh_tmp_file.exe | $PS_GREP '^[0-9]\\+' | $PS_GREP -v UND | awk '{print $1;}' | $PS_GREP -v '^$'", "r");
+	if(!dynsymfile)
+	{
+		perror("Cannot open readeh_tmp_file.exe");
+		exit(2);
+	}
+	auto target=(unsigned int)0;
+	while( fscanf(dynsymfile, "%x", &target) != -1)
+	{
+		possible_target((VirtualOffset_t)target,0,ibt_provenance_t::ibtp_dynsym);
+	}
+}
+
+
+ICFS_t* setup_hellnode(FileIR_t* firp, EXEIO::exeio* elfiop, ibt_provenance_t allowed)
+{
+	auto hn=firp->addNewICFS(nullptr, {}, iasAnalysisModuleComplete);
+
+        for(auto insn: firp->getInstructions())
+	{
+		auto prov=targets[insn->getAddress()->getVirtualOffset()];
+
+		if(prov.isEmpty())
+			continue;
+
+		if(prov.isPartiallySet(allowed))
+		{
+			hn->insert(insn);
+		}
+	}
+
+	if(hn->size() < 1000 && !elfiop->isDynamicallyLinked())
+		hn->setAnalysisStatus(iasAnalysisComplete);
+
+	return hn;
+}
+
+ICFS_t* setup_call_hellnode(FileIR_t* firp, EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t allowed=
+		ibt_provenance_t::ibtp_data |
+		ibt_provenance_t::ibtp_text |
+		ibt_provenance_t::ibtp_stars_addressed |
+		ibt_provenance_t::ibtp_unknown |
+		ibt_provenance_t::ibtp_stars_unreachable |
+	 	ibt_provenance_t::ibtp_dynsym |		// symbol resolved to other module, this module should xfer directly, but could still plt 
+		ibt_provenance_t::ibtp_rodata |
+	 	ibt_provenance_t::ibtp_initarray |	// .init loops through the init_array, and calls them
+	 	ibt_provenance_t::ibtp_finiarray |	// .fini loops through the fini_array, and calls them
+		ibt_provenance_t::ibtp_user;
+
+
+// would like to sanity check better.
+//		ibt_provenance_t::ibtp_stars_data |	// warn if stars reports it's in data, but !allowed.
+
+	/*
+	 * these aren't good enough reasons for a call instruction to transfer somewhere.
+	 * ibt_provenance_t::ibtp_eh_frame	// only libc should xfer.
+	 * ibt_provenance_t::ibtp_gotplt	// only an analyzed jump should xfer.
+	 * ibt_provenance_t::ibtp_entrypoint	// only ld.so or kernel should xfer.
+	 * ibt_provenance_t::ibtp_texttoprintf	// shouldn't xfer if addr passed to printf.
+	 * ibt_provenance_t::ibtp_symtab		// user info only.
+	 * ibt_provenance_t::ibtp_stars_ret	// stars says a return goes here, calls shouldn't.
+	 * ibt_provenance_t::ibtp_stars_switch	// stars says switch target.
+	 * ibt_provenance_t::ibtp_switchtable_type1	// FII switch targets.
+	 * ibt_provenance_t::ibtp_switchtable_type2
+	 * ibt_provenance_t::ibtp_switchtable_type3
+	 * ibt_provenance_t::ibtp_switchtable_type4
+	 * ibt_provenance_t::ibtp_switchtable_type5
+	 * ibt_provenance_t::ibtp_switchtable_type6
+	 * ibt_provenance_t::ibtp_switchtable_type7
+	 * ibt_provenance_t::ibtp_switchtable_type8
+	 * ibt_provenance_t::ibtp_switchtable_type9
+	 * ibt_provenance_t::ibtp_switchtable_type10
+	 */
+
+	auto ret=setup_hellnode(firp,elfiop,allowed);
+
+	cout<<"# ATTRIBUTE fill_in_indtargs::call_hellnode_size="<<dec<<ret->size()<<endl;
+	return ret;
+
+}
+
+ICFS_t* setup_jmp_hellnode(FileIR_t* firp, EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t allowed=
+		ibt_provenance_t::ibtp_data |
+		ibt_provenance_t::ibtp_text |
+		ibt_provenance_t::ibtp_stars_addressed |
+		ibt_provenance_t::ibtp_unknown |
+		ibt_provenance_t::ibtp_stars_unreachable |
+	 	ibt_provenance_t::ibtp_dynsym |		// symbol resolved to other module, this module should xfer directly. but that's not true, may still plt.
+		ibt_provenance_t::ibtp_rodata |
+		ibt_provenance_t::ibtp_gotplt |
+		ibt_provenance_t::ibtp_user;
+
+//		ibt_provenance_t::ibtp_stars_data |	// warn if stars reports it's in data, but !allowed.
+
+	/* 
+	 * these aren't good enough reasons for a jmp instruction to transfer somewhere.
+	 * ibt_provenance_t::ibtp_eh_frame	// only libc should xfer.
+	 * ibt_provenance_t::ibtp_initarray	// only ld.so should xfer.
+	 * ibt_provenance_t::ibtp_finiarray	// only ld.so should xfer.
+	 * ibt_provenance_t::ibtp_entrypoint	// only ld.so or kernel should xfer.
+	 * ibt_provenance_t::ibtp_texttoprintf	// shouldn't xfer if addr passed to printf.
+	 * ibt_provenance_t::ibtp_symtab		// user info only.
+	 * ibt_provenance_t::ibtp_stars_ret	// stars says a return goes here, calls shouldn't.
+	 * ibt_provenance_t::ibtp_stars_switch	// stars says switch target.
+	 * ibt_provenance_t::ibtp_switchtable_type1	// FII switch targets.
+	 * ibt_provenance_t::ibtp_switchtable_type2
+	 * ibt_provenance_t::ibtp_switchtable_type3
+	 * ibt_provenance_t::ibtp_switchtable_type4
+	 * ibt_provenance_t::ibtp_switchtable_type5
+	 * ibt_provenance_t::ibtp_switchtable_type6
+	 * ibt_provenance_t::ibtp_switchtable_type7
+	 * ibt_provenance_t::ibtp_switchtable_type8
+	 * ibt_provenance_t::ibtp_switchtable_type9
+	 * ibt_provenance_t::ibtp_switchtable_type10
+	 */
+
+	auto ret=setup_hellnode(firp,elfiop,allowed);
+	cout<<"# ATTRIBUTE fill_in_indtargs::jmp_hellnode_size="<<dec<<ret->size()<<endl;
+	return ret;
+
+}
+
+
+ICFS_t* setup_ret_hellnode(FileIR_t* firp, EXEIO::exeio* elfiop)
+{
+	ibt_provenance_t allowed=
+		ibt_provenance_t::ibtp_stars_ret |	// stars says a return goes here, and this return isn't analyzeable.
+		ibt_provenance_t::ibtp_unknown |
+		ibt_provenance_t::ibtp_stars_unreachable |
+		ibt_provenance_t::ibtp_ret |	// instruction after a call
+		ibt_provenance_t::ibtp_user;
+
+
+// would like to sanity check better.
+//		ibt_provenance_t::ibtp_stars_data |	// warn if stars reports it's in data, but !allowed.
+
+
+	/*
+	 * these aren't good enough reasons for a ret instruction to transfer somewhere.
+	 * ibt_provenance_t::ibtp_eh_frame	// only libc should xfer.
+	 * ibt_provenance_t::ibtp_initarray	// only ld.so should xfer.
+	 * ibt_provenance_t::ibtp_finiarray	// only ld.so should xfer.
+	 * ibt_provenance_t::ibtp_entrypoint	// only ld.so or kernel should xfer.
+	 * ibt_provenance_t::ibtp_texttoprintf	// shouldn't xfer if addr passed to printf.
+	 * ibt_provenance_t::ibtp_dynsym		// symbol resolved to other module, this module should xfer directly. 
+	 * ibt_provenance_t::ibtp_symtab		// user info only.
+	 * ibt_provenance_t::ibtp_stars_ret	// stars says a return goes here, calls shouldn't.
+	 * ibt_provenance_t::ibtp_stars_switch	// stars says switch target.
+	 * ibt_provenance_t::ibtp_switchtable_type1	// FII switch targets.
+	 * ibt_provenance_t::ibtp_switchtable_type2
+	 * ibt_provenance_t::ibtp_switchtable_type3
+	 * ibt_provenance_t::ibtp_switchtable_type4
+	 * ibt_provenance_t::ibtp_switchtable_type5
+	 * ibt_provenance_t::ibtp_switchtable_type6
+	 * ibt_provenance_t::ibtp_switchtable_type7
+	 * ibt_provenance_t::ibtp_switchtable_type8
+	 * ibt_provenance_t::ibtp_switchtable_type9
+	 * ibt_provenance_t::ibtp_switchtable_type10
+	 * ibt_provenance_t::ibtp_data  	// returns likely shouldn't be used to jump to data or addressed text chunks.  may need to relax later.
+	 * ibt_provenance_t::ibtp_text  
+	 * ibt_provenance_t::ibtp_stars_addressed  
+	 * ibt_provenance_t::ibtp_rodata  
+	 * ibt_provenance_t::ibtp_gotplt  
+	 */
+
+	auto ret_hell_node=setup_hellnode(firp,elfiop,allowed);
+	cout<<"# ATTRIBUTE fill_in_indtargs::basicret_hellnode_size="<<dec<<ret_hell_node->size()<<endl;
+
+	cout<<"# ATTRIBUTE fill_in_indtargs::fullret_hellnode_size="<<dec<<ret_hell_node->size()<<endl;
+	return ret_hell_node;
+}
+
+
+void mark_return_points(FileIR_t* firp)
+{
+
+	// add unmarked return points.  fix_calls will deal with whether they need to be pinned or not later.
+        for(auto insn : firp->getInstructions())
+	{
+		auto d=DecodedInstruction_t::factory(insn);
+		if(string("call")==d->getMnemonic() && insn->getFallthrough())
+		{
+			targets[insn->getFallthrough()->getAddress()->getVirtualOffset()].add(ibt_provenance_t::ibtp_ret);
+		}
+	}
+}
+
+
+void print_icfs(FileIR_t* firp)
+{
+	cout<<"Printing ICFS sets."<<endl;
+        for(auto insn : firp->getInstructions())
+	{
+		auto icfs=insn->getIBTargets();
+
+		// not an IB
+		if(!icfs)
+			continue;
+
+		cout<<hex<<insn->getAddress()->getVirtualOffset()<<" -> ";
+
+		for(auto target : *icfs)
+		{
+			cout<<hex<<target->getAddress()->getVirtualOffset()<<" ";
+		}
+		cout<<endl;
+	}
+}
+
+void setup_icfs(FileIR_t* firp, EXEIO::exeio* elfiop)
+{
+	int total_ibta_set=0;
+
+	/* setup some IBT categories for warning checking */
+        ibt_provenance_t non_stars_data=
+                ibt_provenance_t::ibtp_text |
+                ibt_provenance_t::ibtp_eh_frame |
+                ibt_provenance_t::ibtp_texttoprintf |
+                ibt_provenance_t::ibtp_gotplt |
+                ibt_provenance_t::ibtp_initarray |
+                ibt_provenance_t::ibtp_finiarray |
+                ibt_provenance_t::ibtp_data |
+                ibt_provenance_t::ibtp_dynsym |
+                ibt_provenance_t::ibtp_symtab |
+                ibt_provenance_t::ibtp_rodata |
+                ibt_provenance_t::ibtp_unknown;
+        ibt_provenance_t stars_data=ibt_provenance_t::ibtp_stars_data ;
+
+
+
+	// setup calls, jmps and ret hell nodes.
+	auto call_hell = setup_call_hellnode(firp,elfiop);
+	auto jmp_hell = setup_jmp_hellnode(firp,elfiop);
+	auto ret_hell = setup_ret_hellnode(firp,elfiop);
+
+	// for each instruction 
+        for(auto insn : firp->getInstructions())
+	{
+
+		// if we already got it complete (via stars or FII)
+		if(insn->getIndirectBranchTargetAddress()!=nullptr)
+			total_ibta_set++;
+			
+
+		// warning check
+		ibt_provenance_t prov=targets[insn->getAddress()->getVirtualOffset()];
+
+		// stars calls it data, but printw arning if we didn't find it in data or as a printf addr.
+		if(prov.isPartiallySet(stars_data) && !prov.isPartiallySet(non_stars_data))
+		{
+			//ofstream fout("warning.txt", ofstream::out | ofstream::app);
+			cerr<<"STARS found an IBT in data that FII wasn't able to classify at "<<hex<<insn->getAddress()->getVirtualOffset()<<"."<<endl;
+		}
+
+		// create icfs for complete jump tables.
+		if(jmptables[insn].isComplete())
+		{
+			
+			// get the strcuture into the IRDB	
+			/*
+			auto nn=new ICFS_t(jmptables[insn]);
+			firp->GetAllICFS().insert(nn);
+			insn->SetIBTargets(nn);
+			*/
+			auto nn=firp->addNewICFS(insn,jmptables[insn]);
+
+			if(getenv("IB_VERBOSE")!=0)
+			{
+				cout<<"IB complete for "<<hex<<insn->getAddress()->getVirtualOffset()
+					<<":"<<insn->getDisassembly()<<" with "<<dec<<nn->size()<<" targets."<<endl;
+			}
+
+			// that's all we need to do
+			continue;
+		}
+
+		// disassemble the instruction, and figure out which type of hell node we need.
+		auto d=DecodedInstruction_t::factory(insn);
+		if(d->isReturn()) 
+		{
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"using ret hell node for "<<hex<<insn->getAddress()->getVirtualOffset()<<endl;
+			insn->setIBTargets(ret_hell);
+			ret_hell->insert(ALLOF(jmptables[insn])); // insert any partially analyzed results from rets.
+		}
+		else if ( d->isCall() && (!d->getOperand(0)->isConstant()))
+		{
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"using call hell node for "<<hex<<insn->getAddress()->getVirtualOffset()<<endl;
+			// indirect call 
+			insn->setIBTargets(call_hell);
+			call_hell->insert(ALLOF(jmptables[insn])); // insert any partially analyzed results from calls.
+		}
+		else if ( d->isUnconditionalBranch() && (!d->getOperand(0)->isConstant()))
+		{
+			if(getenv("IB_VERBOSE")!=0)
+				cout<<"using jmp hell node for "<<hex<<insn->getAddress()->getVirtualOffset()<<endl;
+			// indirect jmp 
+			insn->setIBTargets(jmp_hell);
+			jmp_hell->insert(ALLOF(jmptables[insn])); // insert any partially analyzed results from jmps.
+		}
+
+	}
+
+	cout<<"# ATTRIBUTE fill_in_indtargs::total_ibtas_set="<<dec<<total_ibta_set<<endl;
+
+	if(getenv("ICFS_VERBOSE")!=nullptr)
+		print_icfs(firp);
+}
+
+
+void unpin_elf_tables(FileIR_t *firp, int64_t do_unpin_opt)
+{
+	map<string,int> unpin_counts;
+	map<string,int> missed_unpins;
+
+	for(auto scoop : firp->getDataScoops())
+	{
+		// 4 or 8 
+		const auto ptrsize=firp->getArchitectureBitWidth()/8;
+		const char *scoop_contents=scoop->getContents().c_str();
+		if(scoop->getName()==".init_array" || scoop->getName()==".fini_array" || scoop->getName()==".got.plt" || scoop->getName()==".got")
+		{
+			const auto start_offset= (scoop->getName()==".got.plt") ? 3*ptrsize : 0u;
+			for(auto i=start_offset; i+ptrsize <= scoop->getSize() ; i+=ptrsize)
+			{
+				const auto vo=
+					ptrsize==4 ? (VirtualOffset_t)*(uint32_t*)&scoop_contents[i] : 
+					ptrsize==8 ? (VirtualOffset_t)*(uint64_t*)&scoop_contents[i] :
+					throw domain_error("Invalid ptr size");
+
+
+				auto insn=lookupInstruction(firp,vo);
+
+				// OK for .got scoop to miss, some entries are empty.
+				if(scoop->getName()==".got" && insn==nullptr)
+				{
+					if(getenv("UNPIN_VERBOSE")!=0)
+						cout<<"Skipping "<<scoop->getName()<<" unpin for "<<hex<<vo<<" due to no instruction at vo"<<endl;
+					continue;
+				}
+				if(vo==0)
+				{
+					// some segments may be null terminated.
+					assert(i+ptrsize==scoop->getSize());
+					break;
+				}
+
+				// these asserts are probably overkill, but want them for sanity checking for now.
+				assert(insn);
+				assert(targets.find(vo)!=targets.end());
+
+				if( targets[vo].areOnlyTheseSet(
+					ibt_provenance_t::ibtp_initarray | 
+					ibt_provenance_t::ibtp_finiarray | 
+					ibt_provenance_t::ibtp_gotplt    | 
+					ibt_provenance_t::ibtp_got       | 
+					ibt_provenance_t::ibtp_stars_data)
+				  )
+				{
+					total_unpins++;
+					auto allow_unpin=true;
+					if(do_unpin_opt != -1)
+					{
+						if(total_unpins > do_unpin_opt) 
+						{
+						/*
+							cout<<"Aborting unpin process mid elf table."<<endl;
+							return;
+						*/
+							allow_unpin=false;
+						}
+					}
+
+					// when/if they fail, convert to if and guard the reloc creation.
+					if(getenv("UNPIN_VERBOSE")!=0)
+					{
+						if(allow_unpin)
+							cout<<"Attempting unpin #"<<total_unpins<<"."<<endl;
+						else
+							cout<<"Eliding unpin #"<<total_unpins<<"."<<endl;
+					}
+
+					if(allow_unpin || already_unpinned.find(insn)!=already_unpinned.end())
+					{
+						// mark as unpinned
+						already_unpinned.insert(insn);
+						unpin_counts[scoop->getName()]++;
+
+						// add reloc to IR.
+						auto nr=firp->addNewRelocation(scoop, i, "data_to_insn_ptr", insn);
+						assert(nr);
+						/*
+						Relocation_t* nr=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, i, "data_to_insn_ptr", insn);
+						firp->getRelocations().insert(nr);
+						scoop->getRelocations().insert(nr);
+						*/
+
+						if(getenv("UNPIN_VERBOSE")!=0)
+							cout<<"Unpinning "+scoop->getName()+" entry at offset "<<dec<<i<<endl;
+						if(insn->getIndirectBranchTargetAddress()==nullptr)
+						{
+							// add ibta to mark as unpipnned
+							const auto fileid=insn->getAddress()->getFileID();
+							/*
+							auto newaddr = new AddressID_t(BaseObj_t::NOT_IN_DATABASE,fileid,0);
+							assert(newaddr);
+							firp->getAddresses().insert(newaddr);
+							*/
+							auto newaddr=firp->addNewAddress(fileid,0);
+							insn->setIndirectBranchTargetAddress(newaddr);
+						}
+						else
+						{
+							// just mark as unpinned.
+							insn->getIndirectBranchTargetAddress()->setVirtualOffset(0);
+						}	
+					}
+				}
+				else
+				{
+					if(getenv("UNPIN_VERBOSE")!=0)
+						cout<<"Skipping "<<scoop->getName()<<" unpin for "<<hex<<vo<<" due to other references at offset="<<dec<<i<<endl;
+					missed_unpins[scoop->getName()]++;
+				}
+			}
+		}
+		else if(scoop->getName()==".dynsym")
+		{
+			const auto ptrsize=firp->getArchitectureBitWidth()/8;
+			const auto scoop_contents=scoop->getContents().c_str();
+			const auto symsize= 
+				ptrsize==8 ?  sizeof(Elf64_Sym) :
+				ptrsize==4 ?  sizeof(Elf32_Sym) :
+				throw domain_error("Cannot detect ptr size -> ELF symbol mapping");
+
+			auto table_entry_no=0U;
+			for(auto i=0U;i+symsize<scoop->getSize(); i+=symsize, table_entry_no++)
+			{
+				int addr_offset=0;
+				VirtualOffset_t vo=0;
+				int st_info_field=0;
+				int shndx=0;
+				switch(ptrsize)
+				{
+					case 4:
+					{
+						auto sym32=(Elf32_Sym*)&scoop_contents[i];
+						addr_offset=(uintptr_t)&(sym32->st_value)-(uintptr_t)sym32;
+						vo=sym32->st_value;
+						st_info_field=sym32->st_info;
+						shndx=sym32->st_shndx;
+						break;
+					}
+					case 8:
+					{
+						auto sym64=(Elf64_Sym*)&scoop_contents[i];
+						addr_offset=(uintptr_t)&(sym64->st_value)-(uintptr_t)sym64;
+						vo=sym64->st_value;
+						st_info_field=sym64->st_info;
+						shndx=sym64->st_shndx;
+						break;
+					}
+					default:
+						throw domain_error("Invalid pointer size");
+				}
+
+				// this is good for both 32- and 64-bit.
+				int type=ELF32_ST_TYPE(st_info_field);
+
+				if(shndx!=SHN_UNDEF && type==STT_FUNC)
+				{
+					auto insn=lookupInstruction(firp,vo);
+
+					// these asserts are probably overkill, but want them for sanity checking for now.
+					assert(insn);
+					assert(targets.find(vo)!=targets.end());
+
+					// check that the ibt is only ref'd by .dynsym (and STARS, which is ambigulous
+					// about which section 
+					if(targets[vo].areOnlyTheseSet(
+						ibt_provenance_t::ibtp_dynsym | ibt_provenance_t::ibtp_stars_data))
+					{
+						total_unpins++;
+						if(do_unpin_opt != -1)
+						{
+							if(total_unpins > do_unpin_opt) 
+							{
+								cout<<"Aborting unpin process mid elf table."<<endl;
+								return;
+							}
+							cout<<"Attempting unpin #"<<total_unpins<<"."<<endl;
+						}
+
+						if(getenv("UNPIN_VERBOSE")!=0)
+							cout<<"Unpinning .dynsym entry no "<<dec<<table_entry_no<<". vo="<<hex<<vo<<endl;
+
+
+						// when/if these asserts fail, convert to if and guard the reloc creation.
+
+						unpin_counts[scoop->getName()]++;
+						/*
+						auto nr=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, i+addr_offset, "data_to_insn_ptr", insn);
+						assert(nr);
+
+						// add reloc to IR.
+						firp->getRelocations().insert(nr);
+						scoop->getRelocations().insert(nr);
+						*/
+						auto nr=firp->addNewRelocation(scoop, i+addr_offset, "data_to_insn_ptr", insn);
+						(void)nr;
+
+                                                if(insn->getIndirectBranchTargetAddress()==nullptr)
+                                                {
+							/*
+                                                        auto newaddr = new AddressID_t;
+                                                        assert(newaddr);
+                                                        newaddr->SetFileID(insn->getAddress()->getFileID());
+                                                        newaddr->setVirtualOffset(0);   // unpinne
+
+                                                        firp->getAddresses().insert(newaddr);
+							*/
+							auto newaddr=firp->addNewAddress(insn->getAddress()->getFileID(),0);
+                                                        insn->setIndirectBranchTargetAddress(newaddr);
+                                                }
+						else
+                                                {
+                                                        insn->getIndirectBranchTargetAddress()->setVirtualOffset(0);
+                                                }
+					}
+					else
+					{
+						if(getenv("UNPIN_VERBOSE")!=0)
+							cout<<"Skipping .dynsm unpin for "<<hex<<vo<<" due to other references."<<dec<<i<<endl;
+						missed_unpins[scoop->getName()]++;
+					}
+				}
+			}
+		}	
+		else
+		{
+			if(getenv("UNPIN_VERBOSE")!=0)
+				cout<<"Skipping unpin of section "<<scoop->getName()<<endl;
+		}
+			
+	}
+
+	int total_elftable_unpins=0;
+
+	// print unpin stats.
+	for(map<string,int>::iterator it=unpin_counts.begin(); it!=unpin_counts.end(); ++it)
+	{
+		string name=it->first;
+		int count=it->second;
+		cout<<"# ATTRIBUTE fill_in_indtargs::unpin_count_"<<name<<"="<<dec<<count<<endl;
+		total_elftable_unpins++;
+	}
+	for(map<string,int>::iterator it=missed_unpins.begin(); it!=missed_unpins.end(); ++it)
+	{
+		string name=it->first;
+		int count=it->second;
+		cout<<"# ATTRIBUTE fill_in_indtargs::hmissed_unpin_count_"<<name<<"="<<dec<<count<<endl;
+	}
+	cout<<"# ATTRIBUTE fill_in_indtargs::total_elftable_unpins="<<dec<<total_elftable_unpins<<endl;
+
+}
+
+DataScoop_t* find_scoop(FileIR_t *firp, const VirtualOffset_t &vo)
+{
+	for(auto s : firp->getDataScoops())
+	{
+		if( s->getStart()->getVirtualOffset()<=vo && vo<s->getEnd()->getVirtualOffset() )
+			return s;
+	}
+	return nullptr;
+}
+
+// stats for unpinning.
+int type3_unpins=0;
+int type3_pins=0;
+
+void unpin_type3_switchtable(FileIR_t* firp,Instruction_t* insn,DataScoop_t* scoop, int64_t do_unpin_opt)
+{
+
+	assert(firp && insn && scoop);
+
+	set<Instruction_t*> switch_targs;
+
+	if(getenv("UNPIN_VERBOSE"))
+	{
+		cout<<"Unpinning type3 switch, dispatch is "<<hex<<insn->getAddress()->getVirtualOffset()<<":"
+		    <<insn->getDisassembly()<<" with tabSz="<<jmptables[insn].GetTableSize()<<endl; 
+	}
+
+
+	// switch check
+	// could be dangerous if the IBT is found in rodata section,
+	// but then also used for a switch.  this is unlikely.
+	ibt_provenance_t prov=ibt_provenance_t::ibtp_switchtable_type3 |	 // found as switch
+		ibt_provenance_t::ibtp_stars_switch |  	// found as stars switch
+		ibt_provenance_t::ibtp_rodata;		// found in rodata.
+
+	ibt_provenance_t newprov=ibt_provenance_t::ibtp_switchtable_type3 |	 // found as switch
+		ibt_provenance_t::ibtp_stars_switch ;  	// found as stars switch
+
+	// ptr size
+	int ptrsize=firp->getArchitectureBitWidth()/8;
+
+	// offset from start of scoop
+	VirtualOffset_t scoop_off=jmptables[insn].GetTableStart() - scoop->getStart()->getVirtualOffset();
+
+	// scoop contents
+	const char *scoop_contents=scoop->getContents().c_str();
+
+
+	for(int i=0; i<jmptables[insn].GetTableSize(); i++)
+	{
+
+		// grab the value out of the scoop
+		VirtualOffset_t table_entry=0;		
+		switch(ptrsize)
+		{
+			case 4:
+				table_entry=(VirtualOffset_t)*(int*)&scoop_contents[scoop_off];
+				break;
+			case 8:
+				table_entry=(VirtualOffset_t)*(int**)&scoop_contents[scoop_off];
+				break;
+			default:
+				assert(0);
+		}
+
+		// verify we have an instruction.
+		auto ibt=lookupInstruction(firp,table_entry);
+		if(ibt)
+		{
+			// which isn't otherwise addressed.
+			if(targets[table_entry].areOnlyTheseSet(prov))
+			{
+				auto allow_new_unpins=true;
+				total_unpins++;
+				if(do_unpin_opt != -1 && total_unpins > do_unpin_opt) 
+				{
+					allow_new_unpins=false;
+					
+					// don't abort early as we need to fully unpin the IBT once we've started.
+					//cout<<"Aborting unpin process mid switch table."<<endl;
+					// return;
+				}
+
+				// if we are out of unpins, and we haven't unpinned this instruction yet, skip unpinning it.
+				if(!allow_new_unpins && already_unpinned.find(ibt)==already_unpinned.end())
+				{
+					if(getenv("UNPIN_VERBOSE"))
+						cout<<"Eliding switch unpin for entry["<<dec<<i<<"] ibt="<<hex<<table_entry<<", scoop_off="<<scoop_off<<endl;
+
+					// do nothing
+				}
+				else
+				{
+					if(getenv("UNPIN_VERBOSE"))
+						cout<<"Unpinning switch entry ["<<dec<<i<<"] for ibt="<<hex<<table_entry<<", scoop_off="<<scoop_off<<endl;
+					already_unpinned.insert(ibt);
+
+					// add reloc to IR.
+					/*
+					auto nr=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, scoop_off, "data_to_insn_ptr", ibt);
+					assert(nr);
+					firp->getRelocations().insert(nr);
+					scoop->getRelocations().insert(nr);
+					*/
+					auto nr=firp->addNewRelocation(scoop,scoop_off, "data_to_insn_ptr", ibt);
+					(void)nr;
+
+
+					// remove rodata reference for hell nodes.
+					targets[table_entry]=newprov;
+					switch_targs.insert(ibt);
+
+                                         if(ibt->getIndirectBranchTargetAddress()==nullptr)
+                                         {
+						 /*
+                                                 auto newaddr = new AddressID_t;
+                                                 assert(newaddr);
+                                                 newaddr->SetFileID(ibt->getAddress()->getFileID());
+                                                 newaddr->setVirtualOffset(0);   // unpinne
+
+                                                 firp->getAddresses().insert(newaddr);
+						 */
+						 auto newaddr=firp->addNewAddress(ibt->getAddress()->getFileID(),0);
+                                                 ibt->setIndirectBranchTargetAddress(newaddr);
+                                         }
+				         else
+                                         {
+                                                 ibt->getIndirectBranchTargetAddress()->setVirtualOffset(0);
+                                         }
+				}
+			}
+		}
+		scoop_off+=ptrsize;
+		
+		
+	}
+
+	type3_unpins+=switch_targs.size();
+	type3_pins+=jmptables[insn].size();
+
+}
+
+void unpin_switches(FileIR_t *firp, int do_unpin_opt)
+{
+	// re-init stats for this file.
+	type3_unpins=0;
+	type3_pins=0;
+
+	// for each instruction 
+        for(
+                set<Instruction_t*>::const_iterator it=firp->getInstructions().begin();
+                it!=firp->getInstructions().end();
+                ++it
+	   )
+
+        {
+		// check for an insn.
+		Instruction_t* insn=*it;
+		assert(insn);
+
+		// if we didn't find a jmptable for this insn, try again.
+		if(jmptables.find(insn) == jmptables.end())
+			continue;
+
+		// sanity check we have a good switch 
+		if(insn->getIBTargets()==nullptr) continue;
+
+		// sanity check we have a good switch 
+		if(insn->getIBTargets()->getAnalysisStatus()!=iasAnalysisComplete) continue;
+
+		// find the scoop, try next if we fail.
+		DataScoop_t* scoop=find_scoop(firp,jmptables[insn].GetTableStart());
+		if(!scoop) continue;
+
+		if(jmptables[insn].GetSwitchType().areOnlyTheseSet(ibt_provenance_t::ibtp_switchtable_type3))
+		{
+			unpin_type3_switchtable(firp,insn,scoop, do_unpin_opt);
+		}
+        }
+	cout<<"# ATTRIBUTE fill_in_indtargs::switch_type3_pins="<<dec<<type3_pins<<endl;
+	cout<<"# ATTRIBUTE fill_in_indtargs::switch_type3_unpins="<<dec<<type3_unpins<<endl;
+}
+
+void print_unpins(FileIR_t *firp)
+{
+	// don't print if not asked for this type of verbose 
+	if(getenv("UNPIN_VERBOSE") == nullptr)
+		return;
+
+	for(auto scoop : firp->getDataScoops())
+	{
+		assert(scoop);
+		for(auto reloc : scoop->getRelocations())
+		{
+			assert(reloc);
+			cout<<"Found relocation in "<<scoop->getName()<<" of type "<<reloc->getType()<<" at offset "<<hex<<reloc->getOffset()<<endl;
+		}
+	}
+}
+
+
+void unpin_well_analyzed_ibts(FileIR_t *firp, int64_t do_unpin_opt)
+{
+	unpin_elf_tables(firp, do_unpin_opt);
+	unpin_switches(firp, do_unpin_opt);
+	print_unpins(firp);
+}
+
+bool find_arm_address_gen(Instruction_t* insn, const string& reg, VirtualOffset_t& address, bool& page_only) 
+{
+	// init output args, just in case.
+	address=0;
+	page_only=true;
+
+	auto adrp_insn=(Instruction_t*)nullptr;
+	if(backup_until(string()+"adrp "+reg+",",  /* to find */
+			 adrp_insn,                /* return insn here */
+			 insn,                     /* look before here */
+			 "^"+reg+"$",              /* stop if reg is set */
+			 true))                    /* try hard to find the other half, more expensive */
+	{
+		assert(adrp_insn);
+		const auto adrp_disasm=DecodedInstruction_t::factory(adrp_insn);
+		const auto page_no=adrp_disasm->getOperand(1)->getConstant();
+
+		cout<<"Found spilled page_no at "<<hex<<insn->getAddress()->getVirtualOffset()<<" in: "<<endl;
+		cout<<"\t"<<adrp_disasm->getDisassembly()<<endl;
+		cout<<"\t"<<insn->getDisassembly()<<endl;
+		page_only=true;
+		address=page_no;
+		return true;
+	}
+
+	auto add_insn=(Instruction_t*)nullptr;
+	if(backup_until(string()+"add "+reg+",",  /* to find */
+			 add_insn,                /* return insn here */
+			 insn,                    /* look before here */
+			 "^"+reg+"$",             /* stop if reg is set */
+			 true))                   /* try hard to find the other half, more expensive */
+	{
+		assert(add_insn);
+		const auto add_disasm=DecodedInstruction_t::factory(add_insn);
+		const auto add_op1=add_disasm->getOperand(1);
+		const auto add_op2=add_disasm->getOperand(2);
+		if(!add_op1->isRegister()) return false;
+		if( add_op1->getString()=="x29") return false; // skip arm SP.
+		if(!add_op2->isConstant()) return false;
+
+		const auto add_op1_reg=add_op1->getString();
+		const auto add_op2_constant=add_op2->getConstant();
+
+		// try to find an adrp
+		auto adrp_insn=(Instruction_t*)nullptr;
+		if(!backup_until(string()+"adrp "+add_op1_reg+",",  /* to find */
+				 adrp_insn,                         /* return insn here */
+				 add_insn,                          /* look before here */
+				 "^"+add_op1_reg+"$",               /* stop if reg is set */
+				 true)) 			    /* try hard to find the other half, more expensive */
+			return false;
+		assert(adrp_insn);
+
+		const auto adrp_disasm=DecodedInstruction_t::factory(adrp_insn);
+		const auto adrp_page=adrp_disasm->getOperand(1)->getConstant();
+		const auto spilled_address=adrp_page+add_op2_constant;
+		cout<<"Found spilled address at "<<hex<<insn->getAddress()->getVirtualOffset()<<" in: "<<endl;
+		cout<<"\t"<<adrp_disasm->getDisassembly()<<endl;
+		cout<<"\t"<<add_disasm->getDisassembly()<<endl;
+		cout<<"\t"<<insn->getDisassembly()<<endl;
+		page_only=false;
+		address=spilled_address;
+		return true;
+	}
+	return false;
+}
+
+void find_all_arm_unks(FileIR_t* firp)
+{
+	const auto reg_to_spilled_addr=[&](Instruction_t* insn, const string &reg, const SpillPoint_t& spill_loc)
+		{
+
+			auto page_only=true;
+			auto address=VirtualOffset_t(0);
+			if(find_arm_address_gen(insn,reg, address, page_only))
+			{
+				if(page_only)
+					spilled_adrps[spill_loc].insert(address);
+				else
+					spilled_add_adrp_results[spill_loc].insert(address);
+			}
+		};
+	const auto do_verbose=getenv("IB_VERBOSE");
+	/* only valid for arm */
+	if(firp->getArchitecture()->getMachineType() != admtAarch64) return;
+
+	/* find adrps */
+	for(auto insn : firp->getInstructions())
+	{
+		const auto d=DecodedInstruction_t::factory(insn);
+		if(d->getMnemonic()!="adrp") continue;
+		const auto op1=d->getOperand(1);
+		const auto op1_constant=op1->getConstant();
+		all_adrp_results[insn->getFunction()].insert(op1_constant);
+	}
+
+	/* find add/adrp pairs */
+	for(auto insn : firp->getInstructions())
+	{
+		const auto d=DecodedInstruction_t::factory(insn);
+		if(d->getMnemonic()!="add") continue;
+		if(!d->hasOperand(1)) continue;
+		if(!d->hasOperand(2)) continue;
+		const auto op0=d->getOperand(1);
+		const auto op1=d->getOperand(1);
+		const auto op2=d->getOperand(2);
+		if(!op1->isRegister()) continue;
+		if(op1->getString()=="x29") continue; // skip arm SP.
+		if(!op2->isConstant()) continue;
+
+		const auto op1_reg=op1->getString();
+		const auto op2_constant=op2->getConstant();
+
+		// try to find an adrp
+		auto adrp_insn=(Instruction_t*)nullptr;
+		if(!backup_until(string()+"adrp "+op1_reg+",",  /* to find */
+		                 adrp_insn,                     /* return insn here */
+	                	 insn,                          /* look before here */
+	                 	 "^"+op1_reg+"$",               /* stop if reg is set */
+	                 	 true)) 			/* try hard to find the other half, more expensive */
+			continue;
+		assert(adrp_insn);
+
+		const auto adrp_disasm=DecodedInstruction_t::factory(adrp_insn);
+		const auto adrp_page=adrp_disasm->getOperand(1)->getConstant();
+		const auto unk_value=adrp_page+op2_constant;
+
+		all_add_adrp_results     [ insn->getFunction()     ].insert(unk_value);
+		all_add_adrp_results     [ adrp_insn->getFunction()].insert(unk_value);
+		per_reg_add_adrp_results [ op0->getString()        ].insert(unk_value);
+
+		/* check for scoops at the unk address.
+		 * if found, we assume that the unk points at data.
+		 * else, we mark it as a possible code target.
+		 */
+		if(firp->findScoop(unk_value)==nullptr)
+			possible_target(unk_value, 0, ibt_provenance_t::ibtp_text);
+		
+		/* verbose logging */
+		if(do_verbose) 
+			cout << "Detected ARM unk="<<hex<<unk_value<<" for "<<d->getDisassembly()
+			     << " and "<<adrp_disasm->getDisassembly()<<endl;
+
+	}
+	/* find spilled adrp's and add/adrp pairs 
+	 * looking for these patterns:
+	 *
+	 * adrp reg1, #page_no
+	 * add reg2, reg1, #page_offset
+	 * str reg2, [x29, #spill loc]  ; or sp instead of x29
+	 *
+	 * or
+	 *
+	 * adrp reg1, #page_no
+	 * str reg1, [x29, #spill loc]  ; or sp instead of x29
+	 *
+	 * we record these later, in case we find a switch dispatch that has a spilled jump table address.
+	 */
+	for(auto insn : firp->getInstructions())
+	{
+		// look for a spill of an address
+		const auto d=DecodedInstruction_t::factory(insn);
+
+		// spills are str instructions
+		if(d->getMnemonic()!="str") continue;
+
+		// spills of an address are writing an X register. 
+		const auto spill_op0_reg=d->getOperand(0)->getString();
+		if(spill_op0_reg[0]!='x') continue;
+
+		// spills write to the stack with a constant offset.
+		const auto spill_op1=d->getOperand(1);
+		assert(spill_op1->isMemory());
+		const auto spill_op1_string=spill_op1->getString();
+		// needs to have a base reg, which is either sp or x29
+		if(!spill_op1->hasBaseRegister()) continue;
+		if( spill_op1_string.substr(0,2)!="sp" && spill_op1_string.substr(0,3)!="x29" ) continue;
+		if(!spill_op1->hasMemoryDisplacement()) continue;
+		if( spill_op1->hasIndexRegister()) continue;
+
+		const auto spill_disp=spill_op1->getMemoryDisplacement();
+
+		// found str <x-reg> [sp+const]
+
+		reg_to_spilled_addr(insn, spill_op0_reg, SpillPoint_t({insn->getFunction(),spill_disp  }));
+
+
+	}
+	for(auto insn : firp->getInstructions())
+	{
+		// look for a spill of an address
+		const auto d=DecodedInstruction_t::factory(insn);
+
+		// spills are str instructions
+		if(d->getMnemonic()!="stp") continue;
+
+		// spills of an address are writing an X register. 
+		const auto spill_op0_reg=d->getOperand(0)->getString();
+		const auto spill_op1_reg=d->getOperand(1)->getString();
+		if(spill_op0_reg[0]!='x') continue;
+
+		// spills write to the stack with a constant offset.
+		const auto spill_op2=d->getOperand(2);
+		assert(spill_op2->isMemory());
+		const auto spill_op2_string=spill_op2->getString();
+		// needs to have a base reg, which is either sp or x29
+		if(!spill_op2->hasBaseRegister()) continue;
+		if( spill_op2_string.substr(0,2)!="sp" && spill_op2_string.substr(0,3)!="x29" ) continue;
+		if(!spill_op2->hasMemoryDisplacement()) continue;
+		if( spill_op2->hasIndexRegister()) continue;
+
+		const auto spill_disp=spill_op2->getMemoryDisplacement();
+
+		// found stp <xreg> <xreg> [sp+const]
+
+		reg_to_spilled_addr(insn, spill_op0_reg, SpillPoint_t({insn->getFunction(),spill_disp  }));
+		reg_to_spilled_addr(insn, spill_op1_reg, SpillPoint_t({insn->getFunction(),spill_disp+8}));
+
+
+	}
+
+	// look for spilling an address into a d-register.
+	for(auto insn : firp->getInstructions())
+	{
+		// look for moves to d-regs via fmov.
+		const auto d       = DecodedInstruction_t::factory(insn);
+		if( d->getMnemonic()!="fmov" ) continue;
+
+		// look for a spill of an address
+		const auto op0     = d->getOperand(0);
+		const auto op1     = d->getOperand(1);
+		const auto op0_str = op0->getString();
+		const auto op1_str = op1->getString();
+
+		// spills to d-regs are fmov instructions with a d-reg dest and an xreg src.
+		if( op0_str[0]     !='d'    ) continue;
+		if( op1_str[0]     !='x'    ) continue;
+
+		auto page_only=true;
+		auto address=VirtualOffset_t(0);
+		if(find_arm_address_gen(insn,op1_str, address, page_only))
+		{
+			const auto spill_loc = DregSpillPoint_t({insn->getFunction(), op0_str});
+			spilled_to_dreg[spill_loc].insert(address);
+
+		}
+	}
+
+}
+
+
+/*
+ * fill_in_indtargs - main driver routine for 
+ */
+void fill_in_indtargs(FileIR_t* firp, exeio* elfiop, int64_t do_unpin_opt)
+{
+	calc_preds(firp);
+
+	set<VirtualOffset_t> thunk_bases;
+	find_all_module_starts(firp,thunk_bases);
+
+	// reset global vars
+	bounds.clear();
+	ranges.clear();
+	targets.clear();
+	jmptables.clear();
+	already_unpinned.clear();
+	lookupInstruction_init(firp);
+
+
+        int secnum = elfiop->sections.size();
+	int secndx=0;
+
+	/* look through each section and record bounds */
+        for (secndx=0; secndx<secnum; secndx++)
+		get_executable_bounds(firp, elfiop->sections[secndx]);
+
+	/* import info from stars */
+	read_stars_xref_file(firp);
+
+	/* and find any unks ourselves, as stars is unreliable */
+	find_all_arm_unks(firp);
+
+
+	/* look through each section and look for target possibilities */
+        for (secndx=0; secndx<secnum; secndx++)
+		infer_targets(firp, elfiop->sections[secndx]);
+
+	handle_scoop_scanning(firp);
+	
+	/* should move to separate function */
+	for(auto pin : forced_pins )
+		possible_target(pin, 0, ibt_provenance_t::ibtp_user);
+
+	/* look through the instructions in the program for targets */
+	get_instruction_targets(firp, elfiop, thunk_bases);
+
+	/* mark the entry point as a target */
+	possible_target(elfiop->get_entry(),0,ibt_provenance_t::ibtp_entrypoint); 
+
+	/* Read the exception handler frame so that those indirect branches are accounted for */
+	/* then now process the ranges and mark IBTs as necessarthat have exception handling */
+        read_ehframe(firp, elfiop);
+	process_ranges(firp);
+	
+	/* now, find the .GOT addr and process any pc-rel things for x86-32 ibts. */
+	check_for_thunks(firp, thunk_bases);
+
+	/* now deal with dynsym pins */
+	process_dynsym(firp);
+
+	/* mark any instructions after a call instruction */
+	mark_return_points(firp);
+
+	/* set the IR to have some instructions marked as IB targets, and deal with the ICFS */
+	mark_targets(firp);
+	
+
+	cout<<"========================================="<<endl;
+	cout<<"# ATTRIBUTE fill_in_indtargs::total_indirect_targets="<<std::dec<<targets.size()<<endl;
+	print_targets();
+	cout<<"========================================="<<endl;
+
+	// try to setup an ICFS for every IB.
+	setup_icfs(firp, elfiop);
+
+	// do unpinning of well analyzed ibts.
+	if(do_unpin_opt!=(int64_t)-1) 
+		unpin_well_analyzed_ibts(firp, do_unpin_opt);
+
+}
+
+bool split_eh_frame_opt=true;
+int64_t do_unpin_opt=numeric_limits<int64_t>::max() ;
+DatabaseID_t variant_id=BaseObj_t::NOT_IN_DATABASE;
+set<VirtualOffset_t> forced_pins;
+
+int parseArgs(const vector<string> step_args)
+{
+
+	if(step_args.size()<1)
+	{
+		cerr<<"Usage: <id> [--[no-]split-eh-frame] [--[no-]unpin] [addr,...]"<<endl;
+		exit(-1);
+	}
+
+	variant_id=stoi(step_args[0]);
+	cout<<"Parsing parameters with argc= " << step_args.size()<<endl;
+
+	// parse dash-style options.
+	unsigned int argc_iter = 1;
+	while(argc_iter < step_args.size() && step_args[argc_iter][0]=='-')
+	{
+		cout<<"Parsing parameter: "<< step_args[argc_iter] << endl;
+		if(step_args[argc_iter]=="--no-unpin")
+		{
+			do_unpin_opt=-1;
+			argc_iter++;
+		}
+		else if(step_args[argc_iter]=="--unpin")
+		{
+			do_unpin_opt = numeric_limits<decltype(do_unpin_opt)>::max() ;
+			argc_iter++;
+		}
+		else if(step_args[argc_iter]=="--max-unpin" || step_args[argc_iter]=="--max-unpins")
+		{
+			argc_iter++;
+			auto arg_as_str=step_args[argc_iter];
+			argc_iter++;
+
+			try { 
+				do_unpin_opt = stoul(arg_as_str,nullptr,0);
+			}
+			catch (invalid_argument ia)
+			{
+				cerr<<"In --max-unpin, cannot convert "<<arg_as_str<<" to unsigned"<<endl;
+				exit(1);
+			}
+			
+		}
+		else if(step_args[argc_iter]=="--no-split-eh-frame")
+		{
+			split_eh_frame_opt=false;
+			argc_iter++;
+		}
+		else if(step_args[argc_iter]=="--split-eh-frame")
+		{
+			split_eh_frame_opt=true;
+			argc_iter++;
+		}
+		else
+		{
+			cerr<<"Unknown option: "<<step_args[argc_iter]<<endl;
+			return 2;
+		}
+	}
+	// parse addr argumnets 
+	for (; argc_iter < step_args.size(); argc_iter++)
+	{
+		char *end_ptr;
+		VirtualOffset_t offset = strtol(step_args[argc_iter].c_str(), &end_ptr, 0);
+		if (*end_ptr == '\0')
+		{
+			cout << "force pinning: 0x" << std::hex << offset << endl;
+			forced_pins.insert(offset);
+		}
+	}
+
+	cout<<"Setting unpin limit to: "<<dec<<do_unpin_opt<<endl;
+	return 0;
+}
+
+
+int executeStep(IRDBObjects_t *const irdb_objects)
+{
+	//VariantID_t *pidp=nullptr;
+	//FileIR_t * firp=nullptr;
+
+	try 
+	{
+		/* setup the interface to the sql server */
+		const auto pqxx_interface=irdb_objects->getDBInterface();
+		BaseObj_t::setInterface(pqxx_interface);
+
+		auto  pidp = irdb_objects->addVariant(variant_id);
+		assert(pidp);
+
+		// pidp=new VariantID_t(atoi(argv[1]));
+
+
+		assert(pidp->isRegistered()==true);
+
+		cout<<"New Variant, after reading registration, is: "<<*pidp << endl;
+
+		for(const auto &this_file : pidp->getFiles()) 
+		{
+			assert(this_file);
+
+			cout<<"Analyzing file "<<this_file->getURL()<<endl;
+
+			// read the db  
+                        auto firp = irdb_objects->addFileIR(variant_id, this_file->getBaseID());
+			// firp=new FileIR_t(*pidp, this_file);
+			assert(firp);
+
+			firp->setBaseIDS();
+			firp->assembleRegistry();
+
+			// read the executeable file
+			int elfoid=firp->getFile()->getELFOID();
+		        pqxx::largeobject lo(elfoid);
+        		lo.to_file(pqxx_interface->getTransaction(),"readeh_tmp_file.exe");
+        		auto elfiop=unique_ptr<EXEIO::exeio>(new EXEIO::exeio);
+        		elfiop->load(string("readeh_tmp_file.exe"));
+
+			// find all indirect branch targets
+			fill_in_indtargs(firp, elfiop.get(), do_unpin_opt);
+			if(split_eh_frame_opt)
+				split_eh_frame(firp);
+		}
+
+		if(getenv("FII_NOUPDATE")!=nullptr)
+			return -1;
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		return -1;
+        }
+        catch(...)
+        {
+                cerr<<"Unexpected error"<<endl;
+                return -1;
+        }
+
+	assert(getenv("SELF_VALIDATE")==nullptr || bounds.size() > 3 );
+	assert(getenv("SELF_VALIDATE")==nullptr || targets.size() > 100 );
+	assert(getenv("SELF_VALIDATE")==nullptr || ranges.size() > 1 );
+	assert(getenv("SELF_VALIDATE")==nullptr || preds.size() > 100 );
+	assert(getenv("SELF_VALIDATE")==nullptr || lookupInstructionMap.size() > 100 );
+
+	return 0;
+}
+
+std::string getStepName(void) const override
+{
+	return std::string("fill_in_indtargs");
+}
+
+
+};
+
+
+shared_ptr<TransformStep_t> curInvocation;
+
+bool possible_target(VirtualOffset_t p, VirtualOffset_t from_addr, ibt_provenance_t prov)
+{
+	assert(curInvocation);
+	return (dynamic_cast<PopulateIndTargs_t*>(curInvocation.get()))->possible_target(p,from_addr,prov);
+}
+
+void range(VirtualOffset_t start, VirtualOffset_t end)
+{
+	assert(curInvocation);
+	return (dynamic_cast<PopulateIndTargs_t*>(curInvocation.get()))->range(start,end);
+}
+
+extern "C"
+shared_ptr<TransformStep_t> getTransformStep(void)
+{
+        curInvocation.reset(new PopulateIndTargs_t());
+	return curInvocation;
+}
+
+
diff --git a/irdb-lib/ir_builders/fill_in_indtargs.hpp b/irdb-lib/ir_builders/fill_in_indtargs.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..dd0500d1f5ce03c7760387d5739c80d5cdbf1ad2
--- /dev/null
+++ b/irdb-lib/ir_builders/fill_in_indtargs.hpp
@@ -0,0 +1,223 @@
+
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <irdb-core>
+#include <iostream>
+#include <limits>
+#include <stdlib.h>
+#include <string.h>
+#include <map>
+#include <assert.h>
+#include <sys/mman.h>
+#include <sys/types.h>
+#include <regex.h>
+#include <ctype.h>
+#include <list>
+#include <stdio.h>
+
+#include <exeio.h>
+#include "check_thunks.hpp"
+
+
+/*
+ * defines 
+ */
+#define arch_ptr_bytes() (firp->getArchitectureBitWidth()/8u)
+
+/* 
+ * global variables 
+ */
+
+
+//
+// data structures
+//
+
+
+class ibt_provenance_t; 
+static inline std::ostream& operator<<(std::ostream& out, const ibt_provenance_t& prov);
+
+class ibt_provenance_t
+{
+	public:
+		typedef uint32_t provtype_t;
+
+		ibt_provenance_t() : value(0) { };
+
+		ibt_provenance_t(const provtype_t t) : value(t) { };
+
+		static const provtype_t ibtp_eh_frame=1<<0;
+		static const provtype_t ibtp_user=1<<1;	// requested by user
+		static const provtype_t ibtp_gotplt=1<<2;
+		static const provtype_t ibtp_initarray=1<<3;
+		static const provtype_t ibtp_finiarray=1<<4;
+		static const provtype_t ibtp_entrypoint=1<<5;
+		static const provtype_t ibtp_data=1<<6;
+		static const provtype_t ibtp_text=1<<7;
+		static const provtype_t ibtp_texttoprintf=1<<8;
+		static const provtype_t ibtp_dynsym=1<<9;
+		static const provtype_t ibtp_symtab=1<<10;
+		static const provtype_t ibtp_stars_ret=1<<11;
+		static const provtype_t ibtp_stars_switch=1<<12;
+		static const provtype_t ibtp_stars_data=1<<13;
+		static const provtype_t ibtp_stars_unknown=1<<14;
+		static const provtype_t ibtp_stars_addressed=1<<15;
+		static const provtype_t ibtp_stars_unreachable=1<<16;
+		static const provtype_t ibtp_switchtable_type1=1<<17;
+		static const provtype_t ibtp_switchtable_type2=1<<18;
+		static const provtype_t ibtp_switchtable_type3=1<<19;
+		static const provtype_t ibtp_switchtable_type4=1<<20;
+		static const provtype_t ibtp_switchtable_type5=1<<21;
+		static const provtype_t ibtp_switchtable_type6=1<<22;
+		static const provtype_t ibtp_switchtable_type7=1<<23;
+		static const provtype_t ibtp_switchtable_type8=1<<24;
+		static const provtype_t ibtp_switchtable_type9=1<<25;
+		static const provtype_t ibtp_switchtable_type10=1<<26;
+		static const provtype_t ibtp_rodata=1<<27;
+		static const provtype_t ibtp_unknown=1<<28;	// completely unknown
+		static const provtype_t ibtp_got=1<<29;	// got is 0 init'd, shouldn't see this one.
+		static const provtype_t ibtp_ret=1<<30;	// insn after a call
+
+		void add(const provtype_t t) { value |=t; }
+		void add(const ibt_provenance_t t) { value |=t.value; }
+		bool isFullySet(const provtype_t t) const { return (value&t) == t; }
+		bool isFullySet(const ibt_provenance_t t) const { return (value&t.value) == t.value; }
+		bool isPartiallySet(const provtype_t t) const { return (value&t) != 0; }
+		bool isPartiallySet(const ibt_provenance_t t) const { return (value&t.value) != 0; }
+
+		bool areOnlyTheseSet(const provtype_t t) const { return (value&~t) == 0; }
+		bool areOnlyTheseSet(const ibt_provenance_t t) const { return (value&~t.value) == 0; }
+		bool isEmpty() const { return value==0; }
+
+
+	private:
+
+		provtype_t value;
+		friend std::ostream& operator<<(std::ostream& out, const ibt_provenance_t& prov);
+		
+};
+
+static inline std::ostream& operator<<(std::ostream& out, const ibt_provenance_t& prov)
+{
+#define print_prov(a) 						\
+{						 		\
+	if(prov.value&(ibt_provenance_t::a))			\
+	{ 							\
+		const auto foo=std::string(#a);			\
+		out<<foo.substr(4,foo.length())<<",";		\
+	}							\
+}		
+	print_prov(ibtp_eh_frame);
+	print_prov(ibtp_user);
+	print_prov(ibtp_gotplt);
+	print_prov(ibtp_initarray);
+	print_prov(ibtp_finiarray);
+	print_prov(ibtp_entrypoint);
+	print_prov(ibtp_data);
+	print_prov(ibtp_text);
+	print_prov(ibtp_texttoprintf);
+	print_prov(ibtp_dynsym);
+	print_prov(ibtp_symtab);
+	print_prov(ibtp_stars_ret);
+	print_prov(ibtp_stars_switch);
+	print_prov(ibtp_stars_data);
+	print_prov(ibtp_stars_unknown);
+	print_prov(ibtp_stars_addressed);
+	print_prov(ibtp_stars_unreachable);
+	print_prov(ibtp_switchtable_type1);
+	print_prov(ibtp_switchtable_type2);
+	print_prov(ibtp_switchtable_type3);
+	print_prov(ibtp_switchtable_type4);
+	print_prov(ibtp_switchtable_type5);
+	print_prov(ibtp_switchtable_type6);
+	print_prov(ibtp_switchtable_type7);
+	print_prov(ibtp_switchtable_type8);
+	print_prov(ibtp_switchtable_type9);
+	print_prov(ibtp_switchtable_type10);
+	print_prov(ibtp_rodata);
+	print_prov(ibtp_unknown);
+	print_prov(ibtp_got);
+	print_prov(ibtp_ret);
+#undef print_prov
+
+	return out;
+}
+
+
+/*
+ * Forward prototypes 
+ */
+
+bool is_possible_target(IRDB_SDK::VirtualOffset_t p, IRDB_SDK::VirtualOffset_t addr);
+bool possible_target(IRDB_SDK::VirtualOffset_t p, IRDB_SDK::VirtualOffset_t from_addr, ibt_provenance_t prov=ibt_provenance_t::ibtp_unknown);
+
+
+class fii_icfs  : public IRDB_SDK::InstructionSet_t
+{
+	public:
+		// get/set table start
+		IRDB_SDK::VirtualOffset_t GetTableStart() {return table_start; }
+		void SetTableStart(IRDB_SDK::VirtualOffset_t s) {table_start=s; }
+
+		// get/set switch type
+		ibt_provenance_t GetSwitchType() { return switch_type; }
+		void AddSwitchType(const ibt_provenance_t& p) { switch_type.add(p); }
+
+		// get/set table size
+		int GetTableSize() { return table_size; }
+		void SetTableSize(int s) { table_size=s; }
+
+                void addTargets(const IRDB_SDK::InstructionSet_t &other)
+                {
+                        insert(std::begin(other), std::end(other));
+                }
+		bool isIncomplete() const {
+                        return getAnalysisStatus() == IRDB_SDK::iasAnalysisIncomplete;
+                }
+
+                bool isComplete() const {
+                        return getAnalysisStatus() == IRDB_SDK::iasAnalysisComplete;
+                }
+
+                bool isModuleComplete() const {
+                        return getAnalysisStatus() == IRDB_SDK::iasAnalysisModuleComplete;
+                }
+
+                void setAnalysisStatus(const IRDB_SDK::ICFSAnalysisStatus_t p_status) {
+                        m_icfs_analysis_status = p_status;
+                }
+
+		IRDB_SDK::ICFSAnalysisStatus_t getAnalysisStatus() const {
+                        return m_icfs_analysis_status;
+                }
+
+
+	private:
+
+		IRDB_SDK::VirtualOffset_t table_start;
+		ibt_provenance_t switch_type;
+		int table_size;
+		IRDB_SDK::ICFSAnalysisStatus_t m_icfs_analysis_status;
+
+};
+
+void split_eh_frame(IRDB_SDK::FileIR_t* firp);
+
diff --git a/irdb-lib/ir_builders/find_strings.cpp b/irdb-lib/ir_builders/find_strings.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e1f7146d093f6f81d99ae6a029d99e919fef350b
--- /dev/null
+++ b/irdb-lib/ir_builders/find_strings.cpp
@@ -0,0 +1,629 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <irdb-cfg.hpp>
+#include <iostream>
+#include <stdlib.h>
+#include <cctype>
+#include <assert.h>
+#include <stdlib.h>
+
+
+#include <exeio.h>
+
+//#include <elf.h>
+#include "targ-config.h"
+#include "elfio/elfio.hpp"
+//#include "elfio/elfio_dump.hpp"
+
+// elfio doesn't have this, and elf.h does, but including both is troublesome.
+#ifndef SHT_GNU_HASH
+#define SHT_GNU_HASH	  0x6ffffff6
+#endif
+
+
+
+using namespace libIRDB;
+using namespace std;
+using namespace EXEIO;
+
+#define arch_ptr_bytes() (uintptr_t)(firp->GetArchitectureBitWidth()/8)
+
+bool is_string_character(char c)
+{
+	if(c=='\n') return true;
+	return isprint(c);
+}
+
+
+/* the stuff we need for reading an elf file */
+typedef struct elf_info {
+#if 0
+       	::Elf64_Off sec_hdr_off, sec_off;
+       	::Elf_Half secnum, strndx;
+       	::Elf_Word secsize;
+	::Elf64_Addr got;
+#endif
+	int secnum;
+	VirtualOffset_t got;
+	char const **sec_data;
+	exeio *elfiop;
+} elf_info_t;
+
+void found_string(string s, void* addr)
+{
+	char *buff=(char*)malloc(s.length()+2);
+	char *old_p=buff, *p;
+	// use .data() instead of c_str(); can find multiple C-strings in one string
+	memcpy(buff,s.data(),s.length());
+	buff[s.length()]=0;
+
+	do {
+		// look for new lines in the string
+		// if found, split it up and print out each one as it's own thing.
+		while( ( p=strchr(old_p,'\n')) )
+		{
+			*p=0;
+			if (*old_p != 0)
+			{
+				cout << "Found string: \""<<old_p<<"\" at "<<std::hex<<addr<<std::dec<<endl;
+				old_p=p+1;
+			}
+		} 
+
+		if (*old_p != 0)
+			cout << "Found string: \""<<old_p<<"\" at "<<std::hex<<addr<<std::dec<<endl;
+		old_p = p = old_p + strlen(old_p) + 1;
+	} while (p < buff + s.length());
+}
+
+void load_section(elf_info_t &ei, int i, bool alloc)
+{
+	if( alloc && !ei.elfiop->sections[i]->isLoadable()) // (ei.elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC)
+	{
+		cerr<<"Cannot load non-alloc section\n";
+		assert(0);
+	}
+
+	if(ei.sec_data[i]==NULL)
+	{
+		ei.sec_data[i]=ei.elfiop->sections[i]->get_data(); 
+		// if(ei.elfiop->sections[i]->get_type()==SHT_NOBITS)
+		if(ei.elfiop->sections[i]->isBSS())
+		{
+			/* no need to read anything for NOBITS sections */
+			ei.sec_data[i]=(char*)calloc(ei.elfiop->sections[i]->get_size(),1);
+		}
+	}
+}
+
+void check_for_string(const char* p, void* addr)
+{
+	assert(p);
+	if(!is_string_character(*p))
+		return;
+
+	string s;
+	while(*p)
+	{
+		if(!is_string_character(*p))
+			return;
+		s+=*p;
+		p++;
+	}
+	found_string(s, addr);
+}
+
+void is_string_pointer(void* addr, elf_info_t &ei)
+{
+	auto intaddr=(uintptr_t)(addr);
+
+	for(int i=0;i<ei.secnum;i++)
+	{
+//cout << "is_string_pointer(): address: " << std::hex << intaddr << std::dec << "looking at section number: " << i << endl;
+		/* only look at loaded sections */
+		// if( (ei.elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC)
+		if( !ei.elfiop->sections[i]->isLoadable())
+			continue;
+
+		if(ei.elfiop->sections[i]->get_address() <= intaddr 
+			&& intaddr <= (ei.elfiop->sections[i]->get_address()+ei.elfiop->sections[i]->get_size()))
+		{
+			/* we found a pointer into a loadable segment */
+			load_section(ei,i,true);
+
+			check_for_string(ei.sec_data[i]+((long long int)addr-ei.elfiop->sections[i]->get_address()),addr);
+		}
+	}
+
+}
+
+void is_string_constant(const DecodedInstruction_t& disasm)
+{
+	void *addr;
+
+	//if(disasm.Argument1.ArgType != MEMORY_TYPE || disasm.Argument2.ArgType == MEMORY_TYPE
+	//   || disasm.Argument1.ArgSize != FileIR_t::GetArchitectureBitWidth() )
+	if(!disasm.getOperand(0).isMemory() || 
+	   disasm.getOperand(1).isMemory() || 
+	   (uintptr_t)disasm.getOperand(0).getArgumentSizeInBits() != (uintptr_t)FileIR_t::GetArchitectureBitWidth() )
+		return;
+
+	// addr = (void*)disasm.Instruction.Immediat;
+	addr = (void*)disasm.getImmediate();
+
+	/* consider that this constant itself may be a string */
+	unsigned char byte1=(((long long unsigned int)addr)>>24)&0xff;
+	unsigned char byte2=(((long long unsigned int)addr)>>16)&0xff;
+	unsigned char byte3=(((long long unsigned int)addr)>>8)&0xff;
+	unsigned char byte4=(long long unsigned int)addr&0xff;
+	
+        /*  
+               mov reg, 0x6161 
+                       addr       = 0x00006161
+                       addr >> 24 = 0          byte1
+                       addr >> 16 = 0          byte2
+                       addr >> 8 = 61          byte3
+                       addr >> 0 = 61          byte4
+               mov reg, 0x61616161 
+
+               mov reg, 0x0000000061616161 
+        */
+// cout << "address: " << std::hex << addr << std::dec << byte1 << " " << byte2 << " " << byte3 << " " << byte4 << endl;
+	if(  
+		(is_string_character(byte1) || byte1==0) &&
+		(is_string_character(byte2) || byte2==0) &&
+		(is_string_character(byte3) || byte3==0) &&
+		(is_string_character(byte4) || byte4==0)
+	  )
+     {
+	char s[5];
+	s[0]=byte4;
+	s[1]=byte3;
+	s[2]=byte2;
+	s[3]=byte1;
+	s[4]=0;
+	if(strlen(s)>0) // only find 2+ character strings this way.
+		found_string(s, addr);
+     }
+
+
+
+} 
+
+void handle_argument(const DecodedOperand_t &arg, elf_info_t &ei, Instruction_t *insn)
+{
+        // if( (arg->ArgType & MEMORY_TYPE) == MEMORY_TYPE )
+        if(arg.isMemory())
+	{
+		/* Only check without GOT offset if type is executable */
+	
+       		// if( ((arg->ArgType & ABSOLUTE_) == ABSOLUTE_)  && !ei.elfiop->isDLL() )
+       		if( !arg.isPcrel()  && !ei.elfiop->isDLL() )
+			//  && ei.elfiop->get_type() == ET_EXEC ) -- checks for .so/.dll vrs .exe.
+			// is_string_pointer((void*)arg->Memory.Displacement,ei);
+			is_string_pointer((void*)arg.getMemoryDisplacement(),ei);
+		else
+			//is_string_pointer((void*)(arg->Memory.Displacement + insn->GetDataBits().size()), ei);
+			is_string_pointer((void*)(arg.getMemoryDisplacement() + insn->GetDataBits().size()), ei);
+
+		/* Check with GOT offset if present */
+		// if ( ei.got && arg->Memory.BaseRegister == REG3 /* ebx */ )
+		if ( ei.got && arg.hasBaseRegister() && arg.getBaseRegister() == 3 /* ebx */ )
+			// is_string_pointer((void*)(arg->Memory.Displacement + ei.got),ei);
+			is_string_pointer((void*)(arg.getMemoryDisplacement() + ei.got),ei);
+	}
+}
+
+
+void read_elf_info(elf_info_t &ei, FileIR_t* firp)
+{
+
+
+        /* Read ELF header */
+//        ei.sec_hdr_off = ei.elfiop->get_sections_offset();
+        ei.secnum = ei.elfiop->sections.size();
+        assert(ei.secnum>0);
+//        ei.strndx = ei.elfiop->get_section_name_str_index();
+
+	ei.sec_data=(char const**)calloc(ei.secnum,sizeof(void*));
+
+	ei.got = 0;
+	/* Get .got or .got.plt address, if any */
+//	if (ei.strndx != SHN_UNDEF)
+//	{
+//		int shstr_sec;
+//		if (ei.strndx < SHN_LORESERVE)
+//			shstr_sec = ei.strndx;
+//		else
+//			shstr_sec = ei.elfiop->sections[0]->get_link();
+//		assert(shstr_sec < ei.secnum);
+//		load_section(ei,shstr_sec,false);
+//		IRDB_Elf_Shdr *shstr_sec_hdr = ei.sechdrs + shstr_sec;
+		for (int i=0;i<ei.secnum;i++)
+		{
+// name works oddly here.  we can just get the name safely using elfio
+//			assert(ei.sechdrs[i].sh_name < shstr_sec_hdr->sh_size);
+			if (ei.elfiop->sections[i]->get_name()==".got.plt") // !strcmp(ei.sec_data[shstr_sec]+ei.sechdrs[i].sh_name, ".got.plt"))
+			{
+				// Prefer .got.plt to .got
+				ei.got = ei.elfiop->sections[i]->get_address();
+				break;
+			}
+			if (ei.elfiop->sections[i]->get_name()==".got") // if (!strcmp(ei.sec_data[shstr_sec]+ei.sechdrs[i].sh_name, ".got"))
+				ei.got = ei.elfiop->sections[i]->get_address();
+		}
+//	}
+}
+
+void free_elf_info(elf_info_t &ei)
+{
+	#define FREE_IF_NOT_NULL(a) { if(a) { free(a); a=NULL; } }
+	FREE_IF_NOT_NULL(ei.sec_data);
+}
+
+void find_strings_in_instructions(FileIR_t* firp, elf_info_t& ei)
+{
+	set<Instruction_t*> visited_insns;
+
+	// First pass; get strings from basic blocks,
+	// concatenating consecutive immediates stored to the stack
+
+	// Loop over all functions
+	for(
+		set<Function_t*>::const_iterator fit=firp->GetFunctions().begin();
+		fit!=firp->GetFunctions().end();
+		++fit
+	   )
+	{
+		if(!(*fit)->GetEntryPoint())
+			continue;
+		ControlFlowGraph_t cfg = ControlFlowGraph_t(*fit) ;
+		// Loop over basic blocks in function
+		for(
+			set<BasicBlock_t*>::const_iterator bit=cfg.GetBlocks().begin();
+			bit!=cfg.GetBlocks().end();
+			++bit
+		   )
+		{
+			// Loop over instructions in basic block
+			vector<Instruction_t*>::const_iterator iit=(*bit)->GetInstructions().begin();
+			while(iit!=(*bit)->GetInstructions().end())
+			{
+				Instruction_t *insn=*iit;
+				//DISASM disasm;
+				char *str = NULL;
+
+				//int res=Disassemble(insn,disasm);
+				auto disasm=DecodedInstruction_t(insn);
+				int res=disasm.length();
+				assert(res);
+
+				// Concatenate printable strings from consecutive store immediates to SP-relative stack addresses
+				size_t size = 0;
+				unsigned int olddisp = 0;
+				unsigned int newdisp = 0;
+				unsigned int basereg = 0;
+				while(iit!=(*bit)->GetInstructions().end())
+				{
+//					cout<<"Pass 1: Checking insn: "<<disasm.CompleteInstr<<" id: "<<(*iit)->GetBaseID()<<" category: " << (int) (disasm.Instruction.Category & 0xFFFF0000) << " ibta: " << (*iit)->GetIndirectBranchTargetAddress() << endl;
+
+					// Break if not assignment of an immediate to an esp/ebp/eax offset
+//					if (disasm.Argument1.ArgType != MEMORY_TYPE
+//					    || (disasm.Argument1.Memory.BaseRegister != REG4 /* esp */
+//					        && disasm.Argument1.Memory.BaseRegister != REG5 /* ebp */
+//					        && disasm.Argument1.Memory.BaseRegister != REG0 /* eax */)
+//					    || (basereg && disasm.Argument1.Memory.BaseRegister != basereg)
+//					    || disasm.Argument2.ArgType == MEMORY_TYPE
+//					    || ((disasm.Instruction.Category & 0XFFFF0000) != GENERAL_PURPOSE_INSTRUCTION)) 
+					if (!disasm.getOperand(0).isMemory()
+					    || !disasm.getOperand(0).hasBaseRegister()
+					    || (disasm.getOperand(0).getBaseRegister() != 4 /* esp */
+					        && disasm.getOperand(0).getBaseRegister() != 5 /* ebp */
+					        && disasm.getOperand(0).getBaseRegister() != 0 /* eax */)
+					    || (basereg && disasm.getOperand(0).getBaseRegister() != basereg)
+					    || disasm.getOperand(1).isMemory()
+					   )
+					{
+						// mark visited
+						visited_insns.insert(*iit);
+						is_string_constant(disasm);
+						break;
+					}
+					// basereg = disasm.Argument1.Memory.BaseRegister;
+					basereg = disasm.getOperand(0).getBaseRegister();
+					unsigned int disp = disasm.getOperand(0).getMemoryDisplacement();
+					// break if displacement moved backward
+					if (newdisp && (disp < newdisp || disp == olddisp))
+						break;
+					// mark visited
+					visited_insns.insert(*iit);
+					// check for a printable argument
+					// unsigned int imm = disasm.Instruction.Immediat;
+					unsigned int imm = disasm.getImmediate();
+					unsigned char byte1=(imm>>24)&0xff;
+					unsigned char byte2=(imm>>16)&0xff;
+					unsigned char byte3=(imm>>8)&0xff;
+					unsigned char byte4=imm&0xff;
+					// size_t argsize = disasm.Argument1.ArgSize / 8;
+					size_t argsize = disasm.getOperand(0).getArgumentSizeInBytes(); // .ArgSize / 8;
+
+					if ( imm!=0 /* special case 0 which is likely from push <reg> insns, etc. */ && 
+					    (((is_string_character(byte1) || byte1==0) || argsize < 4) &&
+					    ((is_string_character(byte2) || byte2==0) || argsize < 4) &&
+					    ((is_string_character(byte3) || byte3==0) || argsize < 2) &&
+					    (is_string_character(byte4) || byte4==0)))
+					{
+						// printable, concatenate to built string
+						assert(str = (char *)realloc(str, size+argsize));
+						size += argsize;
+						memcpy(str + size - argsize, (char *) (&imm), argsize);
+					}
+					else
+					{
+						// not printable, check for other strings
+						is_string_constant(disasm);
+						break;
+					}
+					++iit;
+					if (iit == (*bit)->GetInstructions().end())
+					{
+						break;
+					}
+					insn = *iit;
+					// break if none
+					if (insn == NULL)
+						break;
+					olddisp = disp;
+					// calculate expected displacement
+					if (newdisp)
+						newdisp += argsize;
+					else
+						newdisp = disp + argsize;
+					// res=Disassemble(insn,disasm);
+					disasm=DecodedInstruction_t(insn);
+					res=disasm.length();
+					assert(res);
+				}
+				
+				// Handle string if one was found
+				if (size > 1) // only find 2+ character strings this way.
+				{
+					if (str[size-1] != 0)
+					{
+						assert(str = (char *)realloc(str, size+1));
+						str[size] = 0;
+						size++;
+					}
+					std::string s(str, size);
+					found_string(s, str);
+					free(str);
+				}
+				// advance to next if we've visited this instruction
+				if (iit != (*bit)->GetInstructions().end()
+				    && visited_insns.find(*iit) != visited_insns.end())
+					++iit;
+			}
+		}
+	}
+
+	// second pass; grab any leftover stringy bits without chunking
+	for(
+		set<Instruction_t*>::const_iterator it=firp->GetInstructions().begin();
+		it!=firp->GetInstructions().end(); 
+		++it
+	   )
+	{
+                Instruction_t *insn=*it;
+
+                //DISASM disasm;
+		//int res=Disassemble(insn,disasm);
+		const auto disasm=DecodedInstruction_t(insn);
+		int res=disasm.length();
+		assert(res);
+//	cout<<"Pass 2: Checking insn: "<<disasm.CompleteInstr<<" id: "<<insn->GetBaseID()<<endl;
+
+		// check for immediate string pointers in non-PIC code
+		if ( !ei.elfiop->isDLL()) // ei.elfiop->get_type() == ET_EXEC )
+			// is_string_pointer((void*)disasm.Instruction.Immediat,ei);
+			is_string_pointer((void*)disasm.getImmediate(),ei);
+		// always check for string pointers in memory argument displacements
+
+		handle_argument(disasm.getOperand(0),ei, insn);
+		handle_argument(disasm.getOperand(1),ei, insn);
+		handle_argument(disasm.getOperand(2),ei, insn);
+
+		// if not in a function, check for string in immediate
+		if (visited_insns.find(insn) != visited_insns.end())
+		{
+			assert(insn->GetFunction());
+			continue;
+		}
+
+//		if (insn->GetFunction())
+//			cerr << "Warning: instruction at address ID " << insn->GetOriginalAddressID()
+//			     << " is in function " << insn->GetFunction()->GetName() << " but not in its CFG." << endl;
+
+		is_string_constant(disasm);
+	}
+}
+
+
+void find_strings_in_data(FileIR_t* firp, elf_info_t& ei)
+{
+	ELFIO::elfio *the_elfiop=reinterpret_cast<ELFIO::elfio *>(ei.elfiop->get_elfio());
+	if(!the_elfiop)
+		return;
+	for(int i=0;i<ei.secnum;i++)
+	{
+		/* skip executable, hash, string table, nonloadable, and tiny sections */
+		if( (the_elfiop->sections[i]->get_flags() & SHF_EXECINSTR)
+		    || the_elfiop->sections[i]->get_type() == SHT_HASH
+		    || the_elfiop->sections[i]->get_type() == SHT_GNU_HASH
+		    || the_elfiop->sections[i]->get_type() == SHT_STRTAB
+		    || (the_elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC
+		    || the_elfiop->sections[i]->get_size() < arch_ptr_bytes())
+			continue;
+
+		auto offset = 0U;
+		auto step = 0U;
+		/* step over relocation info */
+		switch( the_elfiop->sections[i]->get_type() )
+		{
+			case SHT_REL:
+				if(arch_ptr_bytes()==4)
+					step = sizeof(ELFIO::Elf32_Rel);
+				else
+					step = sizeof(ELFIO::Elf64_Rel);
+				break;
+			case SHT_RELA:
+				if(arch_ptr_bytes()==4)
+					step = sizeof(ELFIO::Elf32_Rela);
+				else
+					step = sizeof(ELFIO::Elf64_Rela);
+				break;
+			case SHT_SYMTAB:
+			case SHT_DYNSYM:
+				if(arch_ptr_bytes()==4)
+				{
+					offset = sizeof(ELFIO::Elf32_Word);
+					step = sizeof(ELFIO::Elf32_Sym);
+				}
+				else
+				{
+					offset = sizeof(ELFIO::Elf64_Word);
+					step = sizeof(ELFIO::Elf64_Sym);
+				}
+				break;
+			default:
+				step = 1;
+		}
+
+		load_section(ei,i,true);
+        	for(auto j=offset;(uintptr_t)(j+arch_ptr_bytes())<=(uintptr_t)(ei.elfiop->sections[i]->get_size());j+=step)
+        	{
+			void* p;
+			if(arch_ptr_bytes()==4)
+                		p=(void*)(uintptr_t)*((int*)(ei.sec_data[i]+j));
+			else
+                		p=*((void**)(ei.sec_data[i]+j));
+                	is_string_pointer(p,ei);
+        	}
+
+		
+	}
+	
+}
+
+void find_strings(VariantID_t *pidp, FileIR_t* firp)
+{
+
+	assert(firp && pidp);
+
+	cout<<"Searching variant for strings"<<*pidp<< "." <<endl;
+
+	/* get a handle to the binary file */
+        int elfoid=firp->GetFile()->GetELFOID();
+	pqxxDB_t* pqxx_interface=dynamic_cast<pqxxDB_t*>(BaseObj_t::GetInterface());
+
+	pqxx::largeobject lo(elfoid);
+	lo.to_file(pqxx_interface->GetTransaction(),"readeh_tmp_file.exe");
+	EXEIO::exeio    elfiop;
+	elfiop.load(string("readeh_tmp_file.exe"));
+	//EXEIO::dump::header(cout,elfiop);
+	//EXEIO::dump::section_headers(cout,elfiop);
+
+
+
+
+	elf_info_t ei;
+	ei.elfiop=&elfiop;
+	read_elf_info(ei,firp);
+
+	find_strings_in_instructions(firp, ei);
+	find_strings_in_data(firp, ei);
+
+	free_elf_info(ei);
+
+	cout << "# ATTRIBUTE find_strings::filename="<<firp->GetFile()->GetURL()<<endl;
+}
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: ilr <id>"<<endl;
+		exit(-1);
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t *firp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	cout<<"Reading variant "<<string(argv[1])<<" from database." << endl;
+	try 
+	{
+
+		pidp=new VariantID_t(atoi(argv[1]));
+		assert(pidp->IsRegistered()==true);
+
+
+                for(set<File_t*>::iterator it=pidp->GetFiles().begin();
+                        it!=pidp->GetFiles().end();
+                        ++it
+                    )
+                {
+                        File_t* this_file=*it;
+                        assert(this_file);
+
+			// read the db  
+			firp=new FileIR_t(*pidp,this_file);
+			
+			// do the finding. 
+			find_strings(pidp, firp);
+
+//			firp->WriteToDB();
+
+			delete firp;
+		}
+
+
+		pqxx_interface.Commit();
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cout<<"Done!"<<endl;
+
+	delete pidp;
+	return 0;
+}
+
diff --git a/irdb-lib/ir_builders/fix_calls.cpp b/irdb-lib/ir_builders/fix_calls.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b35c6f5098993cc18abfb1137cc0837508a46ca5
--- /dev/null
+++ b/irdb-lib/ir_builders/fix_calls.cpp
@@ -0,0 +1,1129 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <irdb-core>
+#include <irdb-cfg>
+#include <algorithm>
+#include <iostream>
+#include <stdlib.h>
+#include <assert.h>
+#include <string.h>
+#include <elf.h>
+#include <set>
+#include <exeio.h>
+
+#include "fill_in_indtargs.hpp"
+
+
+using namespace std;
+using namespace EXEIO;
+using namespace IRDB_SDK;
+
+// macros
+#define ALLOF(a) begin(a),end(a)
+
+
+// externs
+extern void read_ehframe(FileIR_t* firp, EXEIO::exeio* );
+
+class FixCalls_t : public TransformStep_t
+{
+
+public:
+
+class Range_t
+{
+        public:
+                Range_t(VirtualOffset_t p_s, VirtualOffset_t p_e) : m_start(p_s), m_end(p_e) { }
+                Range_t() : m_start(0), m_end(0) { }
+
+                virtual VirtualOffset_t getStart() const { return m_start; }
+                virtual VirtualOffset_t getEnd() const { return m_end; }
+                virtual void setStart(VirtualOffset_t s) { m_start=s; }
+                virtual void setEnd(VirtualOffset_t e) { m_end=e; }
+
+        protected:
+
+                VirtualOffset_t m_start, m_end;
+};
+
+struct Range_tCompare
+{
+        bool operator() (const Range_t &first, const Range_t &second) const
+        {
+                return first.getEnd() < second.getStart();
+        }
+};
+
+using Rangeset_t = std::set<Range_t, Range_tCompare>;
+
+
+
+Rangeset_t eh_frame_ranges;
+size_t no_target_insn=0;
+size_t no_fallthrough_insn=0;
+size_t target_not_in_function=0;
+size_t call_to_not_entry=0;
+size_t thunk_check=0;
+size_t found_pattern=0;
+size_t in_ehframe=0;
+size_t no_fix_for_ib=0;
+size_t no_fix_for_safefn=0;
+size_t other_fixes=0;
+size_t fixed_calls=0;
+size_t not_fixed_calls=0;
+size_t not_calls=0;
+
+bool opt_fix_icalls = false;
+bool opt_fix_safefn = true;
+
+bool check_entry(bool &found, ControlFlowGraph_t* cfg)
+{
+
+	auto entry=cfg->getEntry();
+	found=false;
+
+	for(auto insn : entry->getInstructions())
+	{
+		auto disasmp = DecodedInstruction_t::factory(insn);
+		auto &disasm = *disasmp;
+		if(disasm.setsStackPointer()) {
+			return false;
+		} else {
+			if(getenv("VERBOSE_FIX_CALLS"))
+			{
+				VirtualOffset_t addr = 0;
+				if (insn->getAddress())
+					addr = insn->getAddress()->getVirtualOffset();
+				cout<<"check_entry: does not set stack pointer?"<< " address="
+				    <<hex<<addr<<": "<<insn->getDisassembly()<<endl;
+			}
+		}
+
+		if(strstr(disasm.getDisassembly().c_str(), "[esp]"))
+		{
+			found=true;
+			if(getenv("VERBOSE_FIX_CALLS"))
+			{
+				VirtualOffset_t addr = 0;
+				if (insn->getAddress())
+					addr = insn->getAddress()->getVirtualOffset();
+				cout<<"Needs fix (check_entry): [esp]"<< " address="
+				    <<hex<<addr<<": "<<insn->getDisassembly()<<endl;
+			}
+			return true;
+		}
+	}
+
+	return false;
+}
+
+using ControlFlowGraphMap_t = map<Function_t*, shared_ptr<ControlFlowGraph_t> >;
+ControlFlowGraphMap_t cfg_optimizer;
+
+bool call_needs_fix(Instruction_t* insn)
+{
+
+	for(auto reloc : insn->getRelocations())
+	{
+		if(string("safefr") == reloc->getType())
+			return false;
+	}
+
+	auto target=insn->getTarget();
+	auto fallthru=insn->getFallthrough();
+
+	string pattern;
+
+// this used to work because fill_in_indirects would mark IBTs 
+// while reading the ehframe, which perfectly corresponds to when
+// we need to fix calls due to eh_frame.  However, now STARS also marks
+// return points as IBTs, so we need to re-parse the ehframe and use that instead.
+
+	/* no fallthrough instruction, something is odd here */
+	if(!fallthru)
+	{
+		if(getenv("VERBOSE_FIX_CALLS"))
+		{
+			VirtualOffset_t addr = 0;
+			if (insn->getAddress())
+				addr = insn->getAddress()->getVirtualOffset();
+			cout<<"Needs fix: No fallthrough"<< " address="
+			    <<hex<<addr<<": "<<insn->getDisassembly()<<endl;
+		}
+		no_fallthrough_insn++;
+		return true;
+	}
+
+	auto addr=fallthru->getAddress()->getVirtualOffset();
+	auto rangeiter=eh_frame_ranges.find(Range_t(addr,addr));
+	if(rangeiter != eh_frame_ranges.end())	// found an eh_frame addr entry for this call
+	{
+		in_ehframe++;
+		return true;
+	}
+
+	if (!opt_fix_icalls && insn->getIBTargets() && insn->getIBTargets()->size() > 0) 
+	{
+		/* do not fix indirect calls */
+		no_fix_for_ib++;
+		return false;
+	}
+
+	/* if the target isn't in the IR */
+	if(!target)
+	{
+		/* call 0's aren't to real locations */
+		auto disasm=DecodedInstruction_t::factory(insn);
+		if(disasm->getOperand(0)->isConstant() && disasm->getAddress()==0)
+		{
+			return false;
+		}
+		no_target_insn++;
+
+		if(getenv("VERBOSE_FIX_CALLS"))
+		{
+			VirtualOffset_t addr = 0;
+			if (insn->getAddress())
+				addr = insn->getAddress()->getVirtualOffset();
+			cout<<"Needs fix: No target instruction"<< " address="
+			    <<hex<<addr<<": "<<insn->getDisassembly()<<endl;
+		}
+		/* then we need to fix it */
+		return true;
+	}
+
+
+	/* if the location after the call is marked as an IBT, then 
+	 * this location might be used for walking the stack 
+  	 */
+
+
+	auto func=target->getFunction();
+
+	/* if there's no function for this instruction */
+	if(!func)
+	{
+		if(getenv("VERBOSE_FIX_CALLS"))
+		{
+			VirtualOffset_t addr = 0;
+			if (insn->getAddress())
+				addr = insn->getAddress()->getVirtualOffset();
+			cout<<"Needs fix: Target not in a function"<< " address="
+			    <<hex<<addr<<": "<<insn->getDisassembly()<<endl;
+		}
+		target_not_in_function++;
+		/* we need to fix it */
+		return true;
+	}
+
+
+
+	const auto is_found_it=cfg_optimizer.find(func);
+	const auto is_found=(is_found_it!=end(cfg_optimizer));
+
+	if(!is_found)
+		/* build a cfg for this function */
+		cfg_optimizer[func]=shared_ptr<ControlFlowGraph_t>(move(ControlFlowGraph_t::factory(func)));
+
+	auto cfg=cfg_optimizer[func].get();
+	
+
+
+	assert(cfg->getEntry());
+	
+	/* if the call instruction isn't to a function entry point */
+	if(cfg->getEntry()->getInstructions()[0]!=target)
+	{
+		call_to_not_entry++;
+		/* then we need to fix it */
+		return true;
+	}
+
+
+	/* check the entry block for thunks, etc. */
+	auto found=false;
+	bool ret=check_entry(found,cfg);
+	// delete cfg;
+	if(found)
+	{
+		if(ret)
+		{
+			if(getenv("VERBOSE_FIX_CALLS"))
+			{
+				VirtualOffset_t addr = 0;
+				if (insn->getAddress())
+					addr = insn->getAddress()->getVirtualOffset();
+				cout<<"Needs fix: (via check_entry) Thunk detected"<< " address="
+				    <<hex<<addr<<": "<<insn->getDisassembly()<<endl;
+			}
+			thunk_check++;
+		}
+
+		return ret;
+	}
+
+
+	/* otherwise, we think it's safe */
+	return false;
+
+}
+
+/*
+ * - adjust_esp_offset - take newbits, and determine if it has an esp+K type offset in a memory address.
+ * if so, adjust k by offset, and return the new string.
+ */
+string adjust_esp_offset(string newbits, int offset)
+{
+
+        /*
+         * call has opcodes of:
+         *              E8 cw   call near, relative, displacement relative to next instruction
+         *              E8 cd   call near, relative, displacement relative to next instruction
+         *              FF /2   call near, absolute indirect, address given in r/m16
+         *              FF /2   call near, absolute indirect, address given in r/m32
+         *              9a cd   call far, absolute, address given in operand
+         *              9a cp   call far, absolute, address given in operand
+         *              FF /3   call far, absolute indirect, address given in m16:16
+         *              FF /3   call far, absolute indirect, address given in m16:32
+         *
+         *              FF /4   jmp near, absolute indirect, address given in r/m16
+         *              FF /4   jmp near, absolute indirect, address given in r/m32
+         *              FF /5   jmp near, absolute indirect, address given in r/m16
+         *              FF /5   jmp near, absolute indirect, address given in r/m32
+         *
+         *              /digit indicates that the Reg/Opcode field (bits 3-5) of the ModR/M byte (opcode[1])
+         *              contains that value as an opcode instead of a register operand indicator.  The instruction only
+         *              uses the R/M field (bits 0-2) as an operand.
+         *
+         *              cb,cw,cd,cp indicates a 1,2,4,6-byte following the opcode is used to specify a
+         *                      code offset and possibly a new code segment
+         *
+         *      I believe we only care about these this version:
+         *              FF /3   call far, absolute indirect, address given in m16:32
+         *      as we're looking for an address on the stack.
+         *
+         *      The ModR/M byte must be Mod=10, Reg/Op=010, R/M=100 aka 0x94 or possibly
+         *                              Mod=01, Reg/Op=100, R/M=100 aka 0x64 or possibly
+         *                              Mod=10, Reg/Op=100, R/M=100 aka 0xa4 or possibly
+         *                              Mod=01, Reg/Op=010, R/M=100 aka 0x54 or possibly
+         *      R/M=100 indicates to read the SIB (see below)
+         *      Mod=10 indicates an 32-bit displacement after the SIB byte
+         *      Mod=01 indicates an  8-bit displacement after the SIB byte
+         *      Reg/Op=010 indicates an opcode that has a /3 after it
+         *      Reg/Op=100 indicates an opcode that has a /5 after it
+         *
+         *      The SIB byte (opcode[2]) needs to be scale=00, index=100, base=100, or 0x24
+         *              indicating that the addresing mode is 0*%esp+%esp.
+         *
+         *      I believe that the SIB byte could also be 0x64, 0xA4, or 0xE4, but that
+         *      these are very rarely used as they are redundant.
+         *
+         *
+         *
+         *
+         */
+        /* non-negative offsets please */
+        assert(offset>=0);
+
+        int sib_byte=(unsigned char)newbits[2];
+        int sib_base=(unsigned char)sib_byte&0x7;
+        //int sib_ss=(sib_byte>>3)&0x7;
+        //int sib_index=(sib_byte>>3)&0x7;
+
+
+        /* 32-bit offset */
+        if ( (unsigned char)newbits[0] == 0xff &&                                	/* ff */
+             ((unsigned char)newbits[1] == 0x94 || (unsigned char)newbits[1] == 0x64 )    && 		/* /2  or /4*/
+             sib_base == 0x4 )                                          /* base==esp */
+        {
+		// reconstruct the old 32-bit value
+		int oldval=((unsigned char)newbits[6]<<24)+((unsigned char)newbits[5]<<16)+((unsigned char)newbits[4]<<8)+((unsigned char)newbits[3]);
+
+		// add the offset 
+		int newval=oldval+offset;
+
+		// break it back apart to store in the string.
+		newbits[3]=(char)(newval>>0)&0xff;
+		newbits[4]=(char)(newval>>8)&0xff;
+		newbits[5]=(char)(newval>>16)&0xff;
+		newbits[6]=(char)(newval>>24)&0xff;
+        }
+
+        /* 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 */
+        {
+                /* 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)
+                 * if the const offset is over (0x7f-offset), adding offset will overflow it to be negative instead
+                 * of positive
+                 */
+                if((unsigned char)newbits[3]>=(0x7f-offset))
+                {
+                        /* Careful, adding 4 to this will cause an overflow.
+                         * We need to convert it to a 32-bit displacement
+                         */
+                        /* first, change addressing mode from 8-bit to 32-bit. */
+                        newbits[1]&=0x3f;         /* remove upper 2 bits */
+                        newbits[1]|=0x80;         /* make them 10 to indicate a 32-bit offset */
+
+			// sign-extend to 32-bit int
+			int oldval=(char)newbits[3];
+
+			// add the offset 
+			int newval=oldval+offset;
+	
+			// break it back apart to store in the string.
+			assert(newbits.length() == 4);
+			newbits[3]=(char)(newval>>0)&0xff;
+			// 3 most significant bytes extend the instruction
+			newbits+=(char)(newval>>8)&0xff;
+			newbits+=(char)(newval>>16)&0xff;
+			newbits+=(char)(newval>>24)&0xff;
+
+                }
+                else
+
+                        newbits[3] += (char)offset;
+        }
+	return newbits;
+}
+
+	
+
+/* 
+ * convert_to_jump - assume newbits is a call insn, convert newbits to a jump, and return it.
+ * Also: if newbits is a call [esp+k], add "offset" to k.
+ */ 
+void convert_to_jump(Instruction_t* insn, int offset)
+{
+	string newbits=insn->getDataBits();
+	auto dp=DecodedInstruction_t::factory(insn);
+	auto &d=*dp;
+
+	/* this case is odd, handle it specially (and more easily to understand) */
+	if(strcmp(d.getDisassembly().c_str(), "call qword [rsp]")==0)
+	{
+		char buf[100];
+		sprintf(buf,"jmp qword [rsp+%d]", offset);
+		insn->assemble(buf);
+		return;
+	}
+
+
+	/* skip over any prefixes */
+	int op_index=d.getPrefixCount(); // d.Prefix.Number;
+
+	// on the opcode.  assume no prefix here 	
+	switch((unsigned char)newbits[op_index])
+	{
+		// opcodes: ff /2 and ff /3
+		case 0xff:	
+		{
+			// opcode: ff /2
+			// call r/m32, call near, absolute indirect, address given in r/m32
+			if(((((unsigned char)newbits[op_index+1])&0x38)>>3) == 2)
+			{
+				newbits=adjust_esp_offset(newbits,offset);
+				// convert to jmp r/m32
+				// opcode: FF /4
+				newbits[op_index+1]&=0xC7;	// remove old bits
+				newbits[op_index+1]|=(0x4<<3);	// set r/m field to 4
+			}
+			// opcode: ff /3
+			// call m16:32, call far, absolute indirect, address given in m16:32	
+			else if(((((unsigned char)newbits[op_index+1])&0x38)>>3) == 3)
+			{
+				// convert to jmp m16:32
+				// opcode: FF /5
+				newbits[op_index+1]&=0xC7;	// remove old bits
+				newbits[op_index+1]|=(0x5<<3);	// set r/m field to 5
+			}
+			else
+				assert(0);
+			break;
+		}
+		// opcode: 9A cp
+		// call ptr16:32, call far, absolute, address given in operand
+		case 0x9A:	
+		{
+			// convert to jmp ptr16:32
+			// opcode: EA cp
+			newbits[op_index+0]=0xEA;
+			break;
+		}
+
+		// opcode: E8 cd
+		// call rel32, call near, relative, displacement relative to next insn.
+		case 0xE8:
+		{
+			// convert to jmp rel32
+			// opcode: E9 cd
+			newbits[op_index+0]=0xE9;
+			break;
+		}
+
+		// not a call
+		default:
+			assert(0);
+	}
+
+	/* set the instruction's bits */
+	insn->setDataBits(newbits);
+	return;
+}
+
+
+/* 
+ * fix_call - convert call to push/jump.
+ */
+void fix_call(Instruction_t* insn, FileIR_t *firp, bool can_unpin)
+{
+	if(firp->getArchitecture()->getMachineType()==admtAarch64)
+		return;
+
+	/* record the possibly new indirect branch target if this call gets fixed */
+	Instruction_t* newindirtarg=insn->getFallthrough();
+
+        /* Disassemble the instruction */
+	auto disasmp=DecodedInstruction_t::factory (insn);
+	auto &disasm=*disasmp;
+
+	/* if this instruction is an inserted call instruction than we don't need to 
+	 * convert it for correctness' sake.
+	 */
+	if(insn->getAddress()->getVirtualOffset()==0)
+		return;
+
+	/* if the first byte isn't a call opcode, there's some odd prefixing and we aren't handling it.
+	 * this comes up most frequently in a call gs:0x10 instruction where an override prefix specifes the gs: part.
+	 */
+	if((insn->getDataBits()[0]&0x40)==0x40)
+	{
+		// ignore rex prefixes
+	}
+	else if( (insn->getDataBits()[0]!=(char)0xff) && 
+		 (insn->getDataBits()[0]!=(char)0xe8) && 
+		 (insn->getDataBits()[0]!=(char)0x9a) )
+	{
+		cout<<"Found odd prefixing.\n  Not handling **********************************************"<<endl;
+		assert(0);
+		return;
+	}
+
+	if(getenv("VERBOSE_FIX_CALLS"))
+	{
+		cout<<"Doing a fix_call on "<<std::hex<<insn->getAddress()->getVirtualOffset()<< " which is "<<disasm.getDisassembly() /*.CompleteInstr*/<<endl;
+	}
+
+
+	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 */
+	callinsn->setAddress(calladdr);
+	callinsn->setTarget(insn->getTarget());
+	callinsn->setFallthrough(NULL);
+	callinsn->setFunction(insn->getFunction());
+	callinsn->setComment(insn->getComment()+" Jump part");
+
+	/* handle ib targets */
+	callinsn->setIBTargets(insn->getIBTargets());
+	insn->setIBTargets(NULL);
+
+	// We need the control transfer instruction to be from the orig program because 
+	// if for some reason it's fallthrough/target isn't in the DB, we need to correctly 
+	// emit fallthrough/target rules
+	callinsn->setOriginalAddressID(insn->getOriginalAddressID());
+	insn->setOriginalAddressID(BaseObj_t::NOT_IN_DATABASE);
+
+	/* set the new instruction's data bits to be a jmp instead of a call */
+	string newbits="";
+
+	/* add 4 (8) if it's an esp(rsp) indirect branch for x86-32 (-64) */ 
+	callinsn->setDataBits(insn->getDataBits());
+	convert_to_jump(callinsn,firp->getArchitectureBitWidth()/8);		
+
+	/* the jump instruction should NOT be indirectly reachable.  We should
+	 * land at the push
+	 */
+	fix_other_pcrel(firp, callinsn, insn->getAddress()->getVirtualOffset());
+	callinsn->setIndirectBranchTargetAddress(NULL);
+
+	/* add the new insn and new address into the list of valid calls and addresses */
+
+
+	/* Convert the old call instruction into a push return_address instruction */
+	insn->setFallthrough(callinsn);
+	insn->setTarget(NULL);
+	newbits=string("");
+	newbits.resize(5);
+	newbits[0]=0x68;	/* assemble an instruction push next_addr */
+	newbits[1]=(next_addr>>0) & 0xff;
+	newbits[2]=(next_addr>>8) & 0xff;
+	newbits[3]=(next_addr>>16) & 0xff;
+	newbits[4]=(next_addr>>24) & 0xff;
+	insn->setDataBits(newbits);
+	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?");
+
+
+
+	/* If the fallthrough is not marked as indirectly branchable-to, then mark it so */
+	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 */
+		newindirtarg->setIndirectBranchTargetAddress(newaddr);
+	
+		// if we're marking this as an IBTA, determine whether we can unpin it or not 
+		if(can_unpin)
+		{
+			if(getenv("VERBOSE_FIX_CALLS"))
+			{
+				cout<<"setting unpin for type="<< reloc->getType()<< " address="
+				    <<hex<<insn->getBaseID()<<":"<<insn->getDisassembly()<<endl;
+			}
+			// set newindirtarg as unpinned
+                        newindirtarg->getIndirectBranchTargetAddress()->setVirtualOffset(0);
+      			reloc->setWRT(newindirtarg);
+		}
+	}
+
+
+	// 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);
+	*/
+}
+
+
+//
+// return true if insn is a call
+//
+bool is_call(Instruction_t* insn)
+{
+        /* Disassemble the instruction */
+	auto disasm=DecodedInstruction_t::factory (insn);
+	return disasm->isCall(); 
+}
+
+bool can_skip_safe_function(Instruction_t *call_insn) 
+{
+	if (!call_insn)
+		return false;
+	if (!is_call(call_insn))
+		return false;
+	Instruction_t *target=call_insn->getTarget();
+	if (!target)
+		return false;
+	auto func=target->getFunction();
+	if (!func)
+		return false;
+
+	/* if the call instruction isn't to a function entry point */
+	if(func->getEntryPoint()!=target)
+	{
+		return false;
+	}
+
+	if (func->isSafe())
+	{
+		cout << "Function " << func->getName() << " is safe" << endl;
+	}
+
+	return func->isSafe();
+}
+
+
+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()  ;}
+};
+
+
+// 
+// Mark ret_point as an unpinned IBT.
+//
+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);
+	
+}
+
+//
+// fix_all_calls - convert calls to push/jump pairs in the IR.  if fix_all is true, all calls are converted, 
+// else we attempt to detect the calls it is safe to convert.
+//
+void fix_all_calls(FileIR_t* firp, bool fix_all)
+{
+
+	auto sorted_insns = set<Instruction_t*,insn_less<Instruction_t*> >(ALLOF(firp->getInstructions()));
+
+	for(auto insn : sorted_insns)
+	{
+		if(getenv("STOP_FIX_CALLS_AT") && fixed_calls>=(size_t)atoi(getenv("STOP_FIX_CALLS_AT")))
+			break;
+
+		if(is_call(insn)) 
+		{
+			if( call_needs_fix(insn) )	// fixing is necessary + unpinning not possible.
+			{
+				fixed_calls++;
+				fix_call(insn, firp, false);
+			}
+			// we've been asked to fix all calls for funsies/cfi
+			// (and a bit about debugging fix-calls that's not important for anyone but jdh.
+			else if ( fix_all || (getenv("FIX_CALL_LIMIT") && not_fixed_calls>=(size_t)atoi(getenv("FIX_CALL_LIMIT"))))
+			{
+				auto fix_me = true;
+				if (!opt_fix_safefn && can_skip_safe_function(insn))
+				{
+					fix_me = false;
+					no_fix_for_safefn++;
+				}
+
+				if(fix_me)
+				{
+					// if we make it here, we know that it was not 100% necessary to fix the call
+					// but we've been asked to anyhow.	
+					fixed_calls++;
+					fix_call(insn, firp, true /* true here indicates that the call can have an unpin reloc -- anh to add option in 3 minutes */);
+				}
+				else
+				{
+					not_fixed_calls++;
+				}
+			}
+			else
+			{
+				if(getenv("VERBOSE_FIX_CALLS"))
+					cout<<"No fix needed, marking ret site IBT, for "<<insn->getAddress()->getVirtualOffset()<<":"<<insn->getDisassembly()<<endl;
+				mark_as_unpinned_ibt(firp, insn->getFallthrough());
+				not_fixed_calls++;
+			}
+		}
+		
+		else
+		{
+			if(getenv("VERBOSE_FIX_CALLS"))
+				cout<<"Not a call "<<insn->getAddress()->getVirtualOffset()<<":"<<insn->getDisassembly()<<endl;
+			not_calls++;
+		}
+	}
+
+	cout << "# ATTRIBUTE fix_calls::fixed_calls="<<std::dec<<fixed_calls<<endl;
+	cout << "# ATTRIBUTE fix_calls::no_fix_needed_calls="<<std::dec<<not_fixed_calls<<endl;
+	cout << "# ATTRIBUTE fix_calls::other_instructions="<<std::dec<<not_calls<<endl;
+	cout << "# ATTRIBUTE fix_calls::fixed_pct="<<std::fixed<<(((float)fixed_calls)/((float)(not_fixed_calls+fixed_calls+not_calls)))*100.00<<"%"<<endl;
+	cout << "# ATTRIBUTE fix_calls::remaining_ratio="<<std::fixed<<((float)not_fixed_calls/((float)(not_fixed_calls+fixed_calls+not_calls)))*100.00<<"%"<<endl;
+	cout << "# ATTRIBUTE fix_calls::other_insts_ratio="<<std::fixed<<((float)not_calls/((float)(not_fixed_calls+fixed_calls+not_calls)))*100.00<<"%"<<endl;
+	cout << "# ATTRIBUTE fix_calls::no_target_insn="<<std::dec<< no_target_insn << endl;
+	cout << "# ATTRIBUTE fix_calls::no_fallthrough_insn="<<std::dec<< no_fallthrough_insn << endl;
+	cout << "# ATTRIBUTE fix_calls::target_not_in_function="<<std::dec<< target_not_in_function << endl;
+	cout << "# ATTRIBUTE fix_calls::call_to_not_entry="<<std::dec<< call_to_not_entry << endl;
+	cout << "# ATTRIBUTE fix_calls::thunk_check="<<std::dec<< thunk_check << endl;
+	cout << "# ATTRIBUTE fix_calls::found_pattern="<<std::dec<< found_pattern << endl;
+	cout << "# ATTRIBUTE fix_calls::in_ehframe="<<std::dec<< in_ehframe << endl;
+	cout << "# ATTRIBUTE fix_calls::no_fix_for_ib="<<std::dec<< no_fix_for_ib << endl;
+	cout << "# ATTRIBUTE fix_calls::no_fix_for_safefn="<<std::dec<< no_fix_for_safefn << endl;
+}
+
+
+//
+//  fix_other_pcrel - add relocations to other instructions that have pcrel bits
+//
+void fix_other_pcrel(FileIR_t* firp, Instruction_t *insn, uintptr_t virt_offset)
+{
+	auto disasm=DecodedInstruction_t::factory(insn);
+	const auto &operands=disasm->getOperands();
+	const auto relop_it=find_if(ALLOF(operands),[](const shared_ptr<DecodedOperand_t>& op)
+		{ return op->isPcrel() ; } );
+	const bool is_rel= relop_it!=operands.end(); 
+
+	/* if this has already been fixed, we can skip it */
+	if(virt_offset==0 || virt_offset==(uintptr_t)-1)
+		return;
+
+	if(is_rel)
+	{
+		const auto &the_arg=*(relop_it->get());	
+		const auto mt=firp->getArchitecture()->getMachineType();
+		if(mt==admtAarch64)
+		{
+			// figure out how to rewrite pcrel arm insns, then change the virt addr
+			// insn->getAddress()->setVirtualOffset(0);	
+		}
+		else if(mt==admtX86_64 ||  mt==admtI386)
+		{
+			assert(the_arg.isMemory());
+			auto offset=disasm->getMemoryDisplacementOffset(&the_arg, insn); 
+			assert(offset>=0 && offset <=15);
+			auto size=the_arg.getMemoryDisplacementEncodingSize(); 
+			assert(size==1 || size==2 || size==4 || size==8);
+
+			if(getenv("VERBOSE_FIX_CALLS"))
+			{
+				cout<<"Found insn with pcrel memory operand: "<<disasm->getDisassembly()
+				    <<" Displacement="<<std::hex<<the_arg.getMemoryDisplacement() << dec
+				    <<" size="<<the_arg.getMemoryDisplacementEncodingSize() <<" Offset="<<offset;
+			}
+
+			/* convert [rip_pc+displacement] addresssing mode into [rip_0+displacement] where rip_pc is the actual PC of the insn, 
+			 * and rip_0 is means that the PC=0. AKA, we are relocating this instruction to PC=0. Later we add a relocation to undo this transform at runtime 
+			 * when we know the actual address.
+			 */
+
+			/* get the data */
+			string data=insn->getDataBits();
+			char cstr[20]={}; 
+			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;
+
+			assert((uintptr_t)(offset+size)<=(uintptr_t)(data.length()));
+			
+			switch(size)
+			{
+				case 4:
+					assert( (uintptr_t)(int)newdisp == (uintptr_t)newdisp);
+					*(int*)offsetptr=newdisp;
+					break;
+				case 1:
+				case 2:
+				case 8:
+				default:
+					assert(0);
+					//assert(("Cannot handle offset of given size", 0));
+			}
+
+			/* put the data back into the insn */
+			data.replace(0, data.length(), cstr, data.length());
+			insn->setDataBits(data);
+
+			other_fixes++;
+
+			disasm=DecodedInstruction_t::factory(insn);
+			if(getenv("VERBOSE_FIX_CALLS"))
+				cout<<" Converted to: "<<disasm->getDisassembly() << endl;
+
+			// and it's important to set the VO to 0, so that the pcrel-ness is calculated correctly.
+			insn->getAddress()->setVirtualOffset(0);	
+		}
+
+		// 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
+
+	}
+}
+
+void fix_safefr(FileIR_t* firp, Instruction_t *insn, uintptr_t virt_offset)
+{
+	/* if this has already been fixed, we can skip it */
+	if(virt_offset==0 || virt_offset==(uintptr_t)-1)
+		return;
+
+	for(auto reloc : insn->getRelocations())
+	{
+		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);
+		}
+	}
+}
+
+
+void fix_other_pcrel(FileIR_t* firp)
+{
+
+	for(auto insn : firp->getInstructions())
+	{
+		fix_other_pcrel(firp,insn, insn->getAddress()->getVirtualOffset());
+		fix_safefr(firp,insn, insn->getAddress()->getVirtualOffset());
+	}
+	cout << "# ATTRIBUTE fix_calls::other_fixes="<<std::dec<<other_fixes<<endl;
+}
+
+//
+// main rountine; convert calls into push/jump statements 
+//
+// int main(int argc, char* argv[])
+
+
+bool fix_all=false;
+bool do_eh_frame=true;
+
+
+int parseArgs(const vector<string> step_args)
+{
+
+	if(step_args.size()<1)
+	{
+		cerr<<"Usage: <id> [--fix-all | --no-fix-all ] [--eh-frame | --no-ehframe] "<<endl;
+		cerr<<" --eh-frame " << endl;
+		cerr<<" --no-eh-frame 		Use (or dont) the eh-frame section to be compatible with exception handling." << endl;
+		cerr<<" --fix-all " << endl;
+		cerr<<" --no-fix-all 		Convert (or don't) all calls to push/jmp pairs."<<endl;
+		cerr<<" --fix-icalls 		Convert (or don't) indirect calls."<<endl;
+		cerr<<" --no-fix-icalls 	Convert (or don't) indirect calls."<<endl;
+		exit(-1);
+	}
+
+	for(unsigned int argc_iter=1; argc_iter<step_args.size(); argc_iter++)
+	{
+		if("--fix-all"==step_args[argc_iter])
+		{
+			fix_all=true;
+		}
+		else if("--no-fix-all"==step_args[argc_iter])
+		{
+			fix_all=false;
+		}
+		else if("--eh-frame"==step_args[argc_iter])
+		{
+			do_eh_frame=true;
+		}
+		else if("--no-eh-frame"==step_args[argc_iter])
+		{
+			do_eh_frame=false;
+		}
+		else if("--fix-icalls"==step_args[argc_iter])
+		{
+			opt_fix_icalls = true;
+		}
+		else if("--no-fix-icalls"==step_args[argc_iter])
+		{
+			opt_fix_icalls = false;
+		}
+		else if("--fix-safefn"==step_args[argc_iter])
+		{
+			opt_fix_safefn = true;
+		}
+		else if("--no-fix-safefn"==step_args[argc_iter])
+		{
+			opt_fix_safefn = false;
+		}
+		else
+		{
+			cerr<<"Unrecognized option: "<<step_args[argc_iter]<<endl;
+			return -1;
+		}
+	}
+	if(getenv("FIX_CALLS_FIX_ALL_CALLS"))
+		fix_all=true;
+
+	variant_id=stoi(step_args[0]);
+	return 0;
+}
+
+DatabaseID_t variant_id=BaseObj_t::NOT_IN_DATABASE;
+
+
+int executeStep(IRDBObjects_t *const irdb_objects)
+{
+
+	cout<<"Reading variant "<<variant_id<<" from database." << endl;
+	try 
+	{
+		/* setup the interface to the sql server */
+                const auto pqxx_interface=irdb_objects->getDBInterface();
+                BaseObj_t::setInterface(pqxx_interface);
+
+		auto  pidp = irdb_objects->addVariant(variant_id);
+		cout<<"Fixing calls->push/jmp in variant "<<*pidp<< "." <<endl;
+
+		assert(pidp->isRegistered()==true);
+
+		for(const auto &this_file : pidp->getFiles())
+                {
+                        assert(this_file);
+
+			// read the db  
+			auto firp = irdb_objects->addFileIR(variant_id, this_file->getBaseID());
+	
+			assert(firp && pidp);
+	
+			eh_frame_ranges.clear();
+                        int elfoid=firp->getFile()->getELFOID();
+                        pqxx::largeobject lo(elfoid);
+                        lo.to_file(pqxx_interface->getTransaction(),"readeh_tmp_file.exe");
+                        EXEIO::exeio*    elfiop=new EXEIO::exeio;
+                        elfiop->load(string("readeh_tmp_file.exe"));
+                        EXEIO::dump::header(cout,*elfiop);
+                        EXEIO::dump::section_headers(cout,*elfiop);
+			// do eh_frame reading as required. 
+			if(do_eh_frame)
+        			read_ehframe(firp, elfiop);
+
+			fix_all_calls(firp,fix_all);
+			fix_other_pcrel(firp);
+
+			cout<<"Done!"<<endl;
+
+		}
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		return -1;
+        }
+        catch(...)
+        {
+                cerr<<"Unexpected error"<<endl;
+                return -1;
+        }
+
+	assert(getenv("SELF_VALIDATE")==nullptr || (fixed_calls + other_fixes) > 5);
+	assert(getenv("SELF_VALIDATE")==nullptr || fix_all || not_fixed_calls > 5);
+
+	return 0;
+}
+
+void range(VirtualOffset_t a, VirtualOffset_t b)
+{
+	// we've found examples of ranges being 0 sized, and it's a bit weird what that means.
+	// it applies to 0 instructions?
+	// skip it, it's likely an invalid FDE.
+	if(a==b)
+		return; 
+	// non-zero sized fde
+	assert(a<b);
+
+	const auto rangeiter=eh_frame_ranges.find(Range_t(a+1,a+1));
+	assert(rangeiter==eh_frame_ranges.end());
+
+	eh_frame_ranges.insert(Range_t(a+1,b));	// ranges are interpreted as (a,b]
+}
+
+bool possible_target(uintptr_t p, uintptr_t at, ibt_provenance_t prov)
+{
+	// used for LDSA
+	return false;
+}
+
+
+std::string getStepName(void) const override
+{
+        return std::string("fix_calls");
+}
+
+}; // end class FixCalls_t
+
+shared_ptr<TransformStep_t> curInvocation;
+
+bool possible_target(VirtualOffset_t p, VirtualOffset_t from_addr, ibt_provenance_t prov)
+{
+        assert(curInvocation);
+        return (dynamic_cast<FixCalls_t*>(curInvocation.get()))->possible_target(p,from_addr,prov);
+}
+
+void range(VirtualOffset_t start, VirtualOffset_t end)
+{
+        assert(curInvocation);
+        return (dynamic_cast<FixCalls_t*>(curInvocation.get()))->range(start,end);
+}
+
+extern "C"
+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-lib/ir_builders/generate_spri.cpp b/irdb-lib/ir_builders/generate_spri.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..6c60fa7deeb3e331c9583b9de58d02832ba1ea7f
--- /dev/null
+++ b/irdb-lib/ir_builders/generate_spri.cpp
@@ -0,0 +1,107 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <utils.hpp> // to_string function from libIRDB
+#include <iostream>
+#include <fstream>
+#include <stdlib.h>
+#include <string.h>
+#include <assert.h>
+
+using namespace libIRDB;
+using namespace std;
+
+//
+// main routine to generate spri rules for a variant.
+//
+int main(int argc, char* argv[])
+{
+	if(argc!=3 && argc!=4)
+	{
+		cerr<<"Usage: generate_spri.exe <is shared object> <variant id> [<output_file>]"<<endl;
+		exit(-1);
+	}
+
+	int with_ilr=!atoi(argv[1]);
+	assert(with_ilr==!!with_ilr);
+
+	string filename;
+	ostream *fout;
+	if(argc==4)
+		fout=new ofstream(argv[3], ios::out);
+	else
+		fout=&cout;
+
+
+	VariantID_t *varidp=NULL;
+	FileIR_t *firp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	try 
+	{
+
+		cerr<<"Looking up variant "<<string(argv[2])<<" from database." << endl;
+		varidp=new VariantID_t(atoi(argv[2]));
+
+		assert(varidp->IsRegistered()==true);
+
+
+                for(set<File_t*>::iterator it=varidp->GetFiles().begin();
+                        it!=varidp->GetFiles().end();
+                        ++it
+                    )
+                {
+                        File_t* this_file=*it;
+                        assert(this_file);
+			cerr<<"Reading variant "<<string(argv[2])<<":"<<this_file->GetURL()
+			   <<" from database." << endl;
+
+			// read the db  
+			firp=new FileIR_t(*varidp,this_file);
+	
+			// ILR only for the main file.
+			firp->GenerateSPRI(*fout, with_ilr && this_file==varidp->GetMainFile());
+			delete firp;
+		}
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cerr<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cerr<<"Done!"<<endl;
+
+	if(fout!=&cout)
+		((ofstream*)fout)->close();
+		
+
+	delete varidp;
+	return 0;
+}
+
+
diff --git a/irdb-lib/ir_builders/ilr.cpp b/irdb-lib/ir_builders/ilr.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a42c1282cba5aba8e8304dea1c20de7a602513ee
--- /dev/null
+++ b/irdb-lib/ir_builders/ilr.cpp
@@ -0,0 +1,183 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+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()  ;}
+};
+
+void do_ilr(VariantID_t *pidp, FileIR_t* firp)
+{
+
+	assert(firp && pidp);
+
+	cout<<"Applying ILR to variant "<<*pidp<< "." <<endl;
+
+	long long unmoved_instr=0, moved_instr=0;
+
+	set<Instruction_t*,insn_less<Instruction_t*> > sorted_insns;
+
+	set<AddressID_t*> newaddressset;
+	for(
+		set<Instruction_t*>::const_iterator it=firp->GetInstructions().begin();
+		it!=firp->GetInstructions().end(); 
+		++it
+	   )
+	{
+		Instruction_t* insn=*it;	
+		sorted_insns.insert(insn);
+	}
+
+	int ilrd_instructions=0;
+
+
+
+	for(
+		set<Instruction_t*,insn_less<Instruction_t*> >::const_iterator it=sorted_insns.begin();
+		it!=sorted_insns.end(); 
+		++it
+	   )
+	{
+		Instruction_t* insn=*it;
+		ilrd_instructions++;
+
+                if(getenv("ILR_NUMINSNSTOTRANSFORM") && ilrd_instructions==atoi(getenv("ILR_NUMINSNSTOTRANSFORM")))
+		{
+			//DISASM d;
+			//Disassemble(insn,d);
+			const auto d=DecodedInstruction_t(insn);
+			cout<<"Aborting after insn #"<<std::dec<<ilrd_instructions<<": "<<d.getDisassembly() << " at "
+				<<std::hex<<insn->GetAddress()->GetVirtualOffset()<<std::dec<<endl; 
+		}
+                if(getenv("ILR_NUMINSNSTOTRANSFORM") && ilrd_instructions>=atoi(getenv("ILR_NUMINSNSTOTRANSFORM")))
+		{
+			newaddressset.insert(insn->GetAddress());
+			if (insn->GetIndirectBranchTargetAddress())
+				newaddressset.insert(insn->GetIndirectBranchTargetAddress());
+			continue;
+		}
+		
+
+		AddressID_t *newaddr=new AddressID_t;
+		newaddr->SetFileID(insn->GetAddress()->GetFileID());
+		insn->SetAddress(newaddr);
+
+		if (insn->GetIndirectBranchTargetAddress())
+		{
+			unmoved_instr++;
+			newaddressset.insert(insn->GetIndirectBranchTargetAddress());
+		}
+		else
+			moved_instr++;
+
+		newaddressset.insert(newaddr);
+	}
+
+	for(
+		DataScoopSet_t::const_iterator it=firp->GetDataScoops().begin();
+		it!=firp->GetDataScoops().end(); 
+		++it
+	   )
+	{
+		newaddressset.insert((*it)->GetStart());
+		newaddressset.insert((*it)->GetEnd());
+	}
+
+	firp->GetAddresses()=newaddressset;
+
+
+	cout << "# ATTRIBUTE ilr::filename="<<firp->GetFile()->GetURL()<<endl;
+	cout << "# ATTRIBUTE ilr::unmoved_instructions="<<std::dec<<unmoved_instr<<endl;
+	cout << "# ATTRIBUTE ilr::moved_instructions="<<std::dec<<moved_instr<<endl;
+	cout << "# ATTRIBUTE ilr::moved_insts_pct="<<std::fixed<<((float)moved_instr/(moved_instr+unmoved_instr))*100.00<<"%"<<endl;
+
+	cout<<"Writing variant "<<*pidp<<" back to database." << endl;
+	firp->WriteToDB();
+}
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: ilr <id>"<<endl;
+		exit(-1);
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t *firp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	cout<<"Reading variant "<<string(argv[1])<<" from database." << endl;
+	try 
+	{
+
+		pidp=new VariantID_t(atoi(argv[1]));
+		assert(pidp->IsRegistered()==true);
+
+
+                for(set<File_t*>::iterator it=pidp->GetFiles().begin();
+                        it!=pidp->GetFiles().end();
+                        ++it
+                    )
+                {
+                        File_t* this_file=*it;
+                        assert(this_file);
+
+			// ilr isnt working for shared libs yet. 
+			// if(this_file!=pidp->GetMainFile())
+			// 	continue;
+
+			// read the db  
+			firp=new FileIR_t(*pidp,this_file);
+			
+			// do the ILRing. 
+			do_ilr(pidp, firp);
+
+			delete firp;
+		}
+
+
+		pqxx_interface.Commit();
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cout<<"Done!"<<endl;
+
+	delete pidp;
+	return 0;
+}
+
diff --git a/irdb-lib/ir_builders/list_programs.cpp b/irdb-lib/ir_builders/list_programs.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ede92ba86e328b0b14c9f85f6e1a1b170cc1fcae
--- /dev/null
+++ b/irdb-lib/ir_builders/list_programs.cpp
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=1)
+	{
+		cerr<<"Usage: list_tests)"<<endl;
+		exit(-1);
+	}
+
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	for(int i=1; true ; i++)
+	{
+		try 
+		{
+			/* try to load the program ID */
+			VariantID_t pid(i);
+			cout<<pid<<endl;
+		}
+		catch (DatabaseError_t pnide)
+		{
+			if(pnide.GetErrorCode()==DatabaseError_t::VariantNotInDatabase)
+				break;
+			else
+			{
+				cout<<"Unexpected database error: "<<pnide<<endl;
+				exit(-1);
+			}
+		};
+	}
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/mark_functions_safe.cpp b/irdb-lib/ir_builders/mark_functions_safe.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..7e27bd7b85cd61fbb6cd36249c8fa51c12c35e8a
--- /dev/null
+++ b/irdb-lib/ir_builders/mark_functions_safe.cpp
@@ -0,0 +1,125 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <fstream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+Function_t* findFunction(FileIR_t* firp, string funcName)
+{
+	assert(firp);
+
+	for(
+		set<Function_t*>::iterator it=firp->GetFunctions().begin();
+		it!=firp->GetFunctions().end();
+		++it
+	   )
+	{
+		Function_t* func=*it;
+		if (!func) continue;
+		if (func->GetName() == funcName)
+		{
+			return func;
+		}
+	}
+
+	return NULL;
+}
+
+void mark_function_safe(FileIR_t* firp, const std::string& function_file)
+{
+	assert(firp);
+
+	std::ifstream ffile(function_file);
+	std::string fn;
+	while (std::getline(ffile, fn))
+	{
+		cerr << "Want to mark: " << fn << " as safe" << endl;
+		Function_t *f = findFunction(firp, fn);
+		if (f)
+		{
+			cerr << "Found in IRDB: Marking " << f->GetName() << " as safe" << endl;
+			f->SetSafe(true);
+		}
+	}
+
+	firp->WriteToDB();
+}
+
+int main(int argc, char* argv[])
+{
+	if(argc!=3)
+	{
+		cerr<<"Usage: mark_function_safe <id> <file_with_functions_to_mark_safe>"<<endl;
+		exit(-1);
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t *firp=NULL;
+	string function_files(argv[2]);
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	cout<<"Reading variant "<<string(argv[1])<<" from database." << endl;
+	try 
+	{
+		pidp=new VariantID_t(atoi(argv[1]));
+		assert(pidp->IsRegistered()==true);
+
+		for(set<File_t*>::iterator it=pidp->GetFiles().begin(); it!=pidp->GetFiles().end(); ++it)
+		{
+			File_t* this_file=*it;
+			assert(this_file);
+
+			// only do main file for now
+			if(this_file!=pidp->GetMainFile())
+				continue;
+
+			// read the db  
+			firp=new FileIR_t(*pidp,this_file);
+			
+			// mark as safe
+			mark_function_safe(firp, function_files);
+
+			delete firp;
+		}
+		pqxx_interface.Commit();
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cout<<"Done!"<<endl;
+
+	delete pidp;
+	return 0;
+}
+
diff --git a/irdb-lib/ir_builders/pin_address.cpp b/irdb-lib/ir_builders/pin_address.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..dc4fc637433461632f9c32a659205d5590232dc3
--- /dev/null
+++ b/irdb-lib/ir_builders/pin_address.cpp
@@ -0,0 +1,145 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+#include <string.h>
+#include <cstring>
+#include <cstdlib>
+
+using namespace libIRDB;
+using namespace std;
+
+/*
+ * Prefix-aware (pa) string to unsigned
+ * long conversion function.
+ */
+unsigned long pa_strtoul(const char * const number)
+{	
+	unsigned long result = 0l;
+	char *end = NULL;
+	int base = 10;
+	int number_len = strlen(number);
+
+	/*
+	 * Determine the base.
+	 */
+	if (number_len >= 2 && number[0] == '0' && 
+	   ((number[1] == 'x') || (number[1] == 'X')))
+		base = 16;
+	else if (number_len >= 1 && number[0] == '0')
+		base = 8;
+
+	result = strtoul(number, &end, base);	
+	if (end == &number[number_len])
+	{
+		return result;
+	}
+	else
+	{
+		return 0;
+	}
+}
+
+int main(int argc, char* argv[])
+{
+	VariantID_t *pidp=NULL;
+	FileIR_t * firp=NULL;
+	unsigned long address_to_pin = 0;
+	bool did_pin = false;
+
+	if(argc != 3)
+	{
+		cerr<<"Usage: pin_address.exe <id> <address>" << endl;
+		exit(-1);
+	}
+
+	address_to_pin = pa_strtoul(argv[2]);
+	try 
+	{
+		/* setup the interface to the sql server */
+		pqxxDB_t pqxx_interface;
+		BaseObj_t::SetInterface(&pqxx_interface);
+
+		pidp=new VariantID_t(atoi(argv[1]));
+
+		assert(pidp->IsRegistered()==true);
+
+		for(set<File_t*>::iterator it=pidp->GetFiles().begin();
+			it!=pidp->GetFiles().end();
+			++it)
+		{
+			File_t* this_file=*it;
+			assert(this_file);
+
+
+			// read the db  
+			firp=new FileIR_t(*pidp, this_file);
+			/*
+			 * put the two nested loops here.
+			 */
+			for(
+			  set<Function_t*>::const_iterator itf=firp->GetFunctions().begin();
+			  itf!=firp->GetFunctions().end();
+			  ++itf
+			  )
+			{
+				Function_t* func=*itf;
+				for(
+				  set<Instruction_t*>::const_iterator it=func->GetInstructions().begin();
+				  it!=func->GetInstructions().end();
+				  ++it)
+				{
+					Instruction_t* insn = *it;
+					if (insn->GetAddress()->GetVirtualOffset() == address_to_pin)
+					{
+						insn->SetIndirectBranchTargetAddress(insn->GetAddress());
+						did_pin = true;
+					}
+				}
+			}
+			firp->WriteToDB();
+			delete firp;
+
+			if (did_pin) {
+				cout <<"Pinned 0x" << hex << address_to_pin
+				     << " in file " << this_file->GetURL()<<endl;
+				break;
+			}
+		}
+
+		pqxx_interface.Commit();
+		if (!did_pin) {
+			cerr << "Oops: Could not find an instruction at 0x" << hex
+			     << address_to_pin << " to pin." << endl;
+		}
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+	}
+
+	assert(firp && pidp);
+
+	delete pidp;
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/print_variant.cpp b/irdb-lib/ir_builders/print_variant.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b45f283fb732bed65efb8e2e97886c7b4a6dcc90
--- /dev/null
+++ b/irdb-lib/ir_builders/print_variant.cpp
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: simple (<pid>)"<<endl;
+		exit(-1);
+	}
+
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+
+	VariantID_t *pidp=NULL;
+	try 
+	{
+		pidp=new VariantID_t(atoi(argv[1]));
+	}
+	catch (DatabaseError_t pnide)
+	{
+		if(pnide.GetErrorCode()==DatabaseError_t::VariantNotInDatabase)
+		{
+			cout<<"Variant "<< argv[1]<< " not found in db"<<endl;
+			exit(-2);
+		}
+       		else
+		{
+			cout<<"Unexpected database error: "<<pnide<<endl;
+			exit(-1);
+		}
+        }
+
+	cout<<"Variant "<< argv[1]<< " found in db: "<<*pidp << endl;
+
+	delete pidp;
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/read_ehframe.cpp b/irdb-lib/ir_builders/read_ehframe.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..17dd5f8c673ec71a17105a50bee17d77e7a79ce9
--- /dev/null
+++ b/irdb-lib/ir_builders/read_ehframe.cpp
@@ -0,0 +1,998 @@
+
+
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <irdb-core>
+#include <iostream>
+#include <algorithm>
+#include <stdlib.h>
+#include <assert.h>
+#include <string.h>
+
+#include <exeio.h>
+
+// disable sign compare warnings in 3rd party code 
+#pragma GCC diagnostic ignored "-Wsign-compare"
+#include "elfio/elfio.hpp"
+#include "elfio/elfio_dump.hpp"
+#pragma GCC diagnostic pop
+
+
+#include "fill_in_indtargs.hpp"
+
+
+using namespace std;
+using namespace IRDB_SDK;
+
+
+
+
+
+
+uint32_t ptrsize=0;
+ELFIO::elfio *elfiop=NULL;
+void* eh_frame_addr=0;
+char* eh_frame_data=0;
+int eh_frame_data_total_size;
+intptr_t eh_offset=0;
+
+
+
+typedef          int  sword;
+typedef unsigned int  uword;
+typedef unsigned int  uaddr;
+typedef          int  saddr;
+typedef unsigned char ubyte;
+typedef struct dwarf_fde fde;
+typedef uintptr_t _Unwind_Ptr;
+
+union unaligned
+{
+  void *p;
+  unsigned u2 __attribute__ ((mode (HI)));
+  unsigned u4 __attribute__ ((mode (SI)));
+  unsigned u8 __attribute__ ((mode (DI)));
+  signed s2 __attribute__ ((mode (HI)));
+  signed s4 __attribute__ ((mode (SI)));
+  signed s8 __attribute__ ((mode (DI)));
+} __attribute__ ((packed));
+
+
+#define DW_EH_PE_absptr         0x00
+#define DW_EH_PE_omit           0xff
+
+#define DW_EH_PE_uleb128        0x01
+#define DW_EH_PE_udata2         0x02
+#define DW_EH_PE_udata4         0x03
+#define DW_EH_PE_udata8         0x04
+#define DW_EH_PE_sleb128        0x09
+#define DW_EH_PE_sdata2         0x0A
+#define DW_EH_PE_sdata4         0x0B
+#define DW_EH_PE_sdata8         0x0C
+#define DW_EH_PE_signed         0x08
+
+#define DW_EH_PE_pcrel          0x10
+#define DW_EH_PE_textrel        0x20
+#define DW_EH_PE_datarel        0x30
+#define DW_EH_PE_funcrel        0x40
+#define DW_EH_PE_aligned        0x50
+
+#define DW_EH_PE_indirect       0x80
+
+#if __SIZEOF_LONG__ >= __SIZEOF_POINTER__
+  typedef long _sleb128_t;
+  typedef unsigned long _uleb128_t;
+#elif __SIZEOF_LONG_LONG__ >= __SIZEOF_POINTER__
+  typedef long long _sleb128_t;
+  typedef unsigned long long _uleb128_t;
+#else
+# error "What type shall we use for _sleb128_t?"
+#endif
+
+
+struct dwarf_cie
+{
+  uword length;
+  sword CIE_id;
+  ubyte version;
+  unsigned char augmentation[1];
+} __attribute__ ((packed, aligned (__alignof__ (void* ))));
+
+
+
+struct dwarf_fde
+{
+  uword length;
+  sword CIE_delta;
+  unsigned char pc_begin[1];
+} __attribute__ ((packed, aligned (__alignof__ (void* ))));
+
+
+struct fde_vector
+{
+  void *orig_data;
+  size_t count;
+  struct dwarf_fde *array[1];
+};
+
+struct object
+{
+  void *pc_begin;
+  void *tbase;
+  void *dbase;
+  union {
+    struct dwarf_fde *single;
+    struct dwarf_fde **array;
+    struct fde_vector *sort;
+  } u;
+
+  union {
+    struct {
+      unsigned long sorted : 1;
+      unsigned long from_array : 1;
+      unsigned long mixed_encoding : 1;
+      unsigned long encoding : 8;
+      /* ??? Wish there was an easy way to detect a 64-bit host here;
+         we've got 32 bits left to play with...  */
+      unsigned long count : 21;
+    } b;
+    size_t i;
+  } s;
+#ifdef DWARF2_OBJECT_END_PTR_EXTENSION
+  char *fde_end;
+#endif
+
+  struct object *next;
+
+};
+
+void * ptr_to_data_to_addr(uintptr_t data_addr);
+void * addr_to_ptr_to_data(uintptr_t to_deref);
+intptr_t addr_to_p_offset(uintptr_t addr);
+
+
+#include "unwind-pe.h"
+
+void * ptr_to_data_to_addr(uintptr_t data_addr)
+{
+	int i;
+	if(eh_frame_data<=(void*)data_addr && 
+		(uintptr_t)data_addr <= (uintptr_t)eh_frame_data+(uintptr_t)eh_frame_data_total_size)
+	{
+		intptr_t offset=((uintptr_t)data_addr-(uintptr_t)eh_frame_data);
+		const char* data=(const char*)(uintptr_t)eh_frame_addr;
+		return (void*)&data[offset];
+	}
+	for(i=0; i<elfiop->sections.size();i++)
+	{
+		// skip sections that aren't loaded.
+		if((elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC)
+			continue;
+		if(elfiop->sections[i]->get_data()<=(void*)data_addr && 
+			(uintptr_t)data_addr < (uintptr_t)elfiop->sections[i]->get_data() + (uintptr_t)elfiop->sections[i]->get_size() )
+		{
+			intptr_t offset=((uintptr_t)data_addr-(uintptr_t)elfiop->sections[i]->get_data());
+			const char* data=(const char*)(uintptr_t)elfiop->sections[i]->get_address();
+			return (void*)&data[offset];
+		}
+	}
+	assert(0);
+}
+
+
+intptr_t addr_to_p_offset(uintptr_t to_deref)
+{
+	int i;
+	for(i=0; i<elfiop->sections.size();i++)
+	{
+		// skip sections that aren't loaded.
+		if((elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC)
+			continue;
+		if(elfiop->sections[i]->get_address()<=to_deref && 
+			to_deref < elfiop->sections[i]->get_address() + elfiop->sections[i]->get_size() )
+		{
+			intptr_t offset=((uintptr_t)to_deref-(uintptr_t)elfiop->sections[i]->get_address());
+			const char* data=elfiop->sections[i]->get_data();
+			return (intptr_t)(to_deref-(uintptr_t)&data[offset]); 
+		}
+	}
+	assert(0);
+}
+
+void * addr_to_ptr_to_data(uintptr_t to_deref)
+{
+	int i;
+	for(i=0; i<elfiop->sections.size();i++)
+	{
+		// skip sections that aren't loaded.
+		if((elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC)
+			continue;
+		if(elfiop->sections[i]->get_address()<=to_deref && 
+			to_deref < elfiop->sections[i]->get_address() + elfiop->sections[i]->get_size() )
+		{
+			intptr_t offset=((uintptr_t)to_deref-(uintptr_t)elfiop->sections[i]->get_address());
+			const char* data=elfiop->sections[i]->get_data();
+			return (void*)&data[offset];
+		}
+	}
+	assert(0);
+}
+
+_Unwind_Internal_Ptr deref_unwind_ptr(uintptr_t to_deref)
+{
+	int i;
+	for(i=0; i<elfiop->sections.size();i++)
+	{
+		// skip sections that aren't loaded.
+		if((elfiop->sections[i]->get_flags() & SHF_ALLOC) != SHF_ALLOC)
+			continue;
+		if(elfiop->sections[i]->get_address()<=to_deref && 
+			to_deref + ptrsize <= elfiop->sections[i]->get_address() + elfiop->sections[i]->get_size() )
+		{
+			intptr_t offset=(to_deref-elfiop->sections[i]->get_address());
+			const char* data=elfiop->sections[i]->get_data();
+			return deref_unwind_ptr_in_memory(&data[offset]);
+		}
+	}
+	assert(0);
+}
+
+struct lsda_header_info
+{
+  _Unwind_Ptr Start;
+  _Unwind_Ptr LPStart;
+  _Unwind_Ptr ttype_base;
+  unsigned char *TType;
+  unsigned char *action_table;
+  unsigned char ttype_encoding;
+  unsigned char call_site_encoding;
+};
+
+
+
+struct object *all_objects=NULL;
+
+void register_frame_info(void *begin, struct object *ob)
+{
+	memset(ob,0,sizeof(struct object));
+
+  	ob->pc_begin = (void *)-1;
+  	ob->tbase = 0;
+  	ob->dbase = 0;
+  	ob->u.single = (struct dwarf_fde *)begin;
+  	ob->s.i = 0;
+  	ob->s.b.encoding = DW_EH_PE_omit;
+#ifdef DWARF2_OBJECT_END_PTR_EXTENSION
+  	ob->fde_end = NULL;
+#endif
+
+  	ob->next = all_objects;
+  	all_objects = ob;
+
+}
+
+struct dwarf_cie * get_cie (struct dwarf_fde *f)
+{
+  	return (struct dwarf_cie*)((long long)&f->CIE_delta - (long long)f->CIE_delta);
+}
+
+fde * next_fde (fde *f)
+{
+  	return (fde *) ((char *) f + f->length + sizeof (f->length));
+}
+
+int last_fde (struct object *obj __attribute__ ((__unused__)), fde *f)
+{
+#ifdef DWARF2_OBJECT_END_PTR_EXTENSION
+  	return (char *)f == obj->fde_end || f->length == 0;
+#else
+  	return f->length == 0;
+#endif
+}
+
+static _Unwind_Ptr
+base_from_object (unsigned char encoding, struct object *ob)
+{
+  if (encoding == DW_EH_PE_omit)
+    return 0;
+
+  switch (encoding & 0x70)
+    {
+    case DW_EH_PE_absptr:
+    case DW_EH_PE_pcrel:
+    case DW_EH_PE_aligned:
+      return 0;
+
+    case DW_EH_PE_textrel:
+      return (_Unwind_Ptr) ob->tbase;
+    case DW_EH_PE_datarel:
+      return (_Unwind_Ptr) ob->dbase;
+    default:
+      assert(0);
+    }
+}
+
+int get_cie_encoding (struct dwarf_cie *cie)
+{
+  unsigned char *aug, *p;
+  _Unwind_Ptr dummy;
+  _uleb128_t utmp;
+  _sleb128_t stmp;
+
+  aug = cie->augmentation;
+  if (aug[0] != 'z')
+    return DW_EH_PE_absptr;
+
+  p = aug + strlen ((char *)aug) + 1; /* Skip the augmentation string.  */
+  p = read_uleb128 (p, &utmp);          /* Skip code alignment.  */
+  p = read_sleb128 (p, &stmp);          /* Skip data alignment.  */
+  if (cie->version == 1)                /* Skip return address column.  */
+    p++;
+  else
+    p = read_uleb128 (p, &utmp);
+
+  aug++;                                /* Skip 'z' */
+  p = read_uleb128 (p, &utmp);          /* Skip augmentation length.  */
+  while (1)
+    {
+      /* This is what we're looking for.  */
+      if (*aug == 'R')
+        return *p;
+      /* Personality encoding and pointer.  */
+      else if (*aug == 'P')
+        {
+          /* ??? Avoid dereferencing indirect pointers, since we're
+             faking the base address.  Gotta keep DW_EH_PE_aligned
+             intact, however.  */
+          p = read_encoded_value_with_base (*p & 0x7F, 0, p + 1, &dummy);
+        }
+      /* LSDA encoding.  */
+      else if (*aug == 'L')
+        p++;
+      /* Otherwise end of string, or unknown augmentation.  */
+      else
+        return DW_EH_PE_absptr;
+      aug++;
+    }
+}
+
+
+
+
+void * read_pointer (void *p) { union unaligned *up = (union unaligned*)p; return (void*)up->p; }
+
+
+unsigned char *
+extract_cie_info (struct dwarf_cie *cie,
+		int *saw_z, 
+		int *lsda_encoding,
+		int *fde_encoding)
+{
+	unsigned char *aug = cie->augmentation;
+	unsigned char *p = aug + strlen ((char *)aug) + 1;
+	unsigned char *ret = NULL;
+	_uleb128_t utmp=0;
+	_sleb128_t stmp=0;
+
+	/* g++ v2 "eh" has pointer immediately following augmentation string,
+	so it must be handled first.  */
+	if (aug[0] == 'e' && aug[1] == 'h')
+	{
+		void* eh_ptr = read_pointer (p);
+		if(getenv("EH_VERBOSE"))
+			cout<<"eh_ptr: "<< std::dec << eh_ptr<<endl;
+		p += ptrsize;
+		aug += 2;
+	}
+
+	/* Immediately following the augmentation are the code and
+	 * data alignment and return address column.  */
+  	p = read_uleb128 (p, &utmp);
+	if(getenv("EH_VERBOSE"))
+		cout<<"code align: "<< std::dec << utmp<<endl;
+  	p = read_sleb128 (p, &stmp);
+	if(getenv("EH_VERBOSE"))
+		cout<<"data align: "<< std::dec << stmp<<endl;
+  	if (cie->version == 1)
+	{
+    		int ret_col= *p++;
+		if(getenv("EH_VERBOSE"))
+			cout<<"ret_col: "<< std::dec << ret_col<<endl;
+	}
+  	else
+    	{
+      		p = read_uleb128 (p, &utmp);
+		if(getenv("EH_VERBOSE"))
+			cout<<"ret_col: "<< std::dec << utmp<<endl;
+    	}
+
+  /* If the augmentation starts with 'z', then a uleb128 immediately
+     follows containing the length of the augmentation field following
+     the size.  */
+  	if (*aug == 'z')
+    	{
+      		p = read_uleb128 (p, &utmp);
+      		ret = p + utmp;
+		*saw_z=1;
+		if(getenv("EH_VERBOSE"))
+			cout<<"Saw z, length: "<<utmp<<endl;
+      		++aug;
+    	}
+
+  /* Iterate over recognized augmentation subsequences.  */
+  	while (*aug != '\0')
+	{
+		/* "L" indicates a byte showing how the LSDA pointer is encoded.  */
+		if (aug[0] == 'L')
+		{
+			*lsda_encoding = *p++;
+			if(getenv("EH_VERBOSE"))
+				cout<<"lsda encoding "<<std::hex<<*lsda_encoding<<endl;
+			aug += 1;
+		}
+
+		/* "R" indicates a byte indicating how FDE addresses are encoded.  */
+		else if (aug[0] == 'R')
+		{
+			*fde_encoding = *p++;
+			if(getenv("EH_VERBOSE"))
+				cout<<"fde encoding "<<std::hex<<*fde_encoding<<endl;
+			aug += 1;
+		}
+
+		/* "P" indicates a personality routine in the CIE augmentation.  */
+		else if (aug[0] == 'P')
+		{
+			_Unwind_Ptr personality=0;
+			int personality_encoding=*p;
+
+
+			p = read_encoded_value_with_base(*p, 0, p + 1, &personality);
+
+			if(getenv("EH_VERBOSE"))
+			{
+				cout << "encoding personality = " << std::hex << personality_encoding << endl;
+				cout << "fs->personality = " << std::hex << personality << endl;
+			}
+			possible_target(personality, 0, ibt_provenance_t::ibtp_eh_frame);
+			aug += 1;
+		}
+
+		/* "S" indicates a signal frame.  */
+		else if (aug[0] == 'S')
+		{
+			if(getenv("EH_VERBOSE"))
+				cout << "fs->signal_frame = 1 " <<  endl;
+			aug += 1;
+		}
+
+		/* Otherwise we have an unknown augmentation string.
+		Bail unless we saw a 'z' prefix.  */
+		else
+			return ret;
+	}
+
+  	return ret ? ret : p;
+}
+
+
+
+static size_t
+classify_object_over_fdes (struct object *ob, fde *this_fde)
+{
+  struct dwarf_cie *last_cie = 0;
+  size_t count = 0;
+  int encoding = DW_EH_PE_absptr;
+  _Unwind_Ptr base = 0;
+
+  for (; ! last_fde (ob, this_fde); this_fde = next_fde (this_fde))
+    {
+//	printf("analysis addr=%p\n", this_fde);
+//	printf("pgm addr=%p\n", (uintptr_t)this_fde+(uintptr_t)eh_offset);
+//	printf("offset=%p\n", (uintptr_t)this_fde+(uintptr_t)eh_offset-(uintptr_t)eh_frame_addr);
+      struct dwarf_cie *this_cie;
+      _Unwind_Ptr mask, pc_begin;
+
+      /* Skip CIEs.  */
+      if (this_fde->CIE_delta == 0)
+        continue;
+
+      /* Determine the encoding for this FDE.  Note mixed encoded
+         objects for later.  */
+      this_cie = get_cie (this_fde);
+      if (this_cie != last_cie)
+        {
+          last_cie = this_cie;
+          encoding = get_cie_encoding (this_cie);
+          base = base_from_object (encoding, ob);
+          if (ob->s.b.encoding == DW_EH_PE_omit)
+            ob->s.b.encoding = encoding;
+          else if (ob->s.b.encoding != encoding)
+            ob->s.b.mixed_encoding = 1;
+        }
+
+      read_encoded_value_with_base (encoding, base, this_fde->pc_begin,
+                                    &pc_begin);
+
+      /* Take care to ignore link-once functions that were removed.
+         In these cases, the function address will be NULL, but if
+         the encoding is smaller than a pointer a true NULL may not
+         be representable.  Assume 0 in the representable bits is NULL.  */
+      mask = size_of_encoded_value (encoding);
+      if (mask < ptrsize)
+        mask = (((_Unwind_Ptr) 1) << (mask << 3)) - 1;
+      else
+        mask = -1;
+
+      if ((pc_begin & mask) == 0)
+        continue;
+
+      count += 1;
+      if ((void *) pc_begin < ob->pc_begin)
+        ob->pc_begin = (void *) pc_begin;
+    }
+
+
+	if(getenv("EH_VERBOSE"))
+		cout<<"Count is "<<count<<endl;
+
+  	return count;
+}
+
+void print_lsda_handlers(lsda_header_info* info, unsigned char* p)
+{
+	// change to lsda section;
+	uintptr_t p_addr=((uintptr_t)p+(uintptr_t)eh_offset);
+
+	// if the action table is size 0, avoid calling addr_to_ptr_to_data on it, because it may assert, 
+	// and we wouldn't do anything (except 0 iterations of the loop below) with the results anyhow.
+	if(p_addr == (uintptr_t)info->action_table)
+		return;
+
+	p=(unsigned char*)addr_to_ptr_to_data((uintptr_t)p_addr);
+	// use -1 in case info->action table represents the end of a section.
+	uintptr_t action_table_in_data=(uintptr_t)addr_to_ptr_to_data((uintptr_t)info->action_table-1);
+//	intptr_t p_offset=(intptr_t)p-(intptr_t)ptr_to_addr_to_data_to_addr((uintptr_t)p);
+  	// Search the call-site table for the action associated with this IP.
+  	while (
+			// use <= because we we used -1 3 lines above.
+			((uintptr_t)p) <=  (uintptr_t)action_table_in_data
+		)
+    	{
+      		_Unwind_Ptr cs_start=0, cs_len=0, cs_lp=0;
+      		_uleb128_t cs_action=0;
+		
+      		// Note that all call-site encodings are "absolute" displacements.
+      		p = read_encoded_value (0, info->call_site_encoding, p, &cs_start);
+      		p = read_encoded_value (0, info->call_site_encoding, p, &cs_len);
+      		p = read_encoded_value (0, info->call_site_encoding, p, &cs_lp);
+      		p = read_uleb128 (p, &cs_action);
+
+		if(cs_lp!=0)
+		{
+
+			if(getenv("EH_VERBOSE"))
+			{
+				cout 	<<"cs_start: "<< cs_start  << "\t"
+					<<"cs_len: "<< cs_len << "\t"
+					<<"cs_lp: "<< cs_lp << "\t"
+					<<"cs_action: "<< cs_action << endl;
+				cout 	<<"cs_start+info->Start: "<< cs_start+info->Start << "\t"
+					<<"cs_len+cs_start+info->Start: "<< cs_len+cs_start+info->Start << "\t"
+					<<"cs_lp+info->LPstart: "<< cs_lp +info->LPStart<< "\t"
+					<<"cs_action: "<< cs_action << endl;
+			}
+
+#ifndef TEST
+
+			/* the landing pad is a possible target if an exception is thrown */ 
+			possible_target(cs_lp+info->Start, 0, ibt_provenance_t::ibtp_eh_frame);
+
+			/* and the return address is a possible oddity if it's used for walking the stack */
+			possible_target(cs_len+cs_start+info->Start, 0, ibt_provenance_t::ibtp_eh_frame);
+
+#endif
+		}
+    	}
+}
+
+int get_fde_encoding (struct dwarf_fde *f)
+{
+  return get_cie_encoding (get_cie (f));
+}
+
+unsigned char * parse_lsda_header (unsigned char *p, lsda_header_info *info, struct object *ob, fde* f)
+{
+  	_uleb128_t tmp=0;
+  	unsigned char lpstart_encoding=0;
+	_Unwind_Ptr func=0;
+
+  	info->Start = 0;
+/*
+fixme
+
+	needs to be info->Start=context->bases->func
+
+
+which is set here:
+*/
+      unsigned char encoding = ob->s.b.encoding;
+      if (ob->s.b.mixed_encoding)
+        encoding = get_fde_encoding (f);
+      read_encoded_value_with_base (encoding, base_from_object (encoding, ob),
+                                    f->pc_begin, (_Unwind_Ptr*)&func);
+
+	info->Start=func;
+	if(getenv("EH_VERBOSE"))
+		cout<<"info->Start set to "<<std::hex << (uintptr_t)info->Start << endl;
+
+
+  	// Find @LPStart, the base to which landing pad offsets are relative.
+  	lpstart_encoding = *p++;
+  	if (lpstart_encoding != DW_EH_PE_omit)
+    		p = read_encoded_value_with_base (lpstart_encoding, 0, p, &info->LPStart);
+  	else
+    		info->LPStart = info->Start;
+
+	if(getenv("EH_VERBOSE"))
+		cout<<"LPStart : "<<std::hex<<info->LPStart<<endl;
+
+  	// Find @TType, the base of the handler and exception spec type data.
+  	info->ttype_encoding = *p++;
+  	if (info->ttype_encoding != DW_EH_PE_omit)
+    	{
+      		p = read_uleb128 (p, &tmp);
+		// this doesn't work
+      		//info->TType = (unsigned char*)ptr_to_data_to_addr((uintptr_t)(p + tmp));
+      		info->TType = p + tmp + eh_offset;
+    	}
+  	else
+    		info->TType = 0;
+
+	if(getenv("EH_VERBOSE"))
+		cout<<"ttype : "<<std::hex<<((uintptr_t)(info->TType))<<endl;
+
+  	// The encoding and length of the call-site table; the action table
+  	// immediately follows.
+  	info->call_site_encoding = *p++;
+
+	if(getenv("EH_VERBOSE"))
+		cout<<"Call site encoding   " << std::hex << (uintptr_t)info->call_site_encoding << endl;
+
+  	p = read_uleb128 (p, &tmp);
+  	info->action_table = p + tmp + eh_offset;
+  	//info->action_table = (unsigned char*)ptr_to_data_to_addr((uintptr_t)(p + tmp));
+	if(getenv("EH_VERBOSE"))
+		cout<<"Action table: "<<std::hex<<(uintptr_t)info->action_table<<endl;
+
+  	return p;
+}
+
+
+
+
+
+void linear_search_fdes (struct object *ob, fde *this_fde, int offset)
+{
+  	struct dwarf_cie *last_cie = 0;
+  	int encoding = ob->s.b.encoding;
+	cout<<"encoding="<<encoding<<endl;
+  	_Unwind_Ptr base = base_from_object (ob->s.b.encoding, ob);
+	int saw_z=0; 
+	int lsda_encoding=DW_EH_PE_omit;
+	int fde_encoding=0;
+	int count=0;
+
+  	for (; ! last_fde (ob, this_fde); this_fde = next_fde (this_fde))
+    	{
+		count++;
+		if(getenv("EH_VERBOSE"))
+		{
+			cout<<"Examining FDE #"<<std::dec<<count<<" at offset "<<hex<<(uintptr_t)this_fde-(uintptr_t)eh_frame_data<<endl;
+			cout<<"FDE (in memory) addr is: "<<std::hex<<this_fde<<endl;
+			cout<<"FDE (in file) addr is: "<<std::hex<<(uintptr_t)this_fde-(uintptr_t)eh_frame_data+(uintptr_t)eh_frame_addr<<endl;
+		}
+      		struct dwarf_cie *this_cie=NULL;
+      		_Unwind_Ptr pc_begin=0, pc_range=0;
+	
+      		/* Skip CIEs.  */
+      		if (this_fde->CIE_delta == 0)
+		{
+			if(getenv("EH_VERBOSE"))
+				cout<<"Skipping FDE because it's a CIE"<<endl;
+        		continue;
+		}
+
+		this_cie = get_cie (this_fde);
+
+		saw_z=0; 
+		lsda_encoding=DW_EH_PE_omit;
+		fde_encoding=0;
+		extract_cie_info(this_cie, &saw_z, &lsda_encoding, &fde_encoding);
+
+  		/* Locate augmentation for the fde.  */
+  		unsigned char* aug = (unsigned char *) this_fde + 8; /* 4-bytes for FDE len, 4-bytes for FDE id. */
+
+		// 2x size of fde_encoding for pc_begin and pc_range */
+  		aug += 2 * size_of_encoded_value (fde_encoding);
+  		if (saw_z)
+    		{
+      			_uleb128_t i=0;
+      			aug = read_uleb128 (aug, &i);
+    		}
+  		if (lsda_encoding != DW_EH_PE_omit)
+    		{
+      			_Unwind_Ptr lsda;
+		
+        		aug = read_encoded_value_with_base (lsda_encoding, 0, aug, &lsda);
+			cout<<"lsda at "<<std::hex << lsda <<endl;
+			lsda_header_info info;
+			memset(&info, 0, sizeof(info));
+			cout.flush();
+	
+			// lsda might be 0, which means we shouldn't load it!
+			if(lsda != 0 ) 
+			{
+				// change sections;
+				uintptr_t save_eh_offset=eh_offset;
+				eh_offset=addr_to_p_offset(lsda);
+				unsigned char* lsda_p=parse_lsda_header (
+					(unsigned char*)addr_to_ptr_to_data(lsda)
+					, &info, ob, this_fde);
+				print_lsda_handlers(&info, lsda_p); 
+				eh_offset=save_eh_offset;
+				cout.flush();
+			}
+    		}
+
+	
+
+      		if (ob->s.b.mixed_encoding)
+        	{
+          		/* Determine the encoding for this FDE.  Note mixed encoded
+             		objects for later.  */
+           		this_cie = get_cie (this_fde);
+          		if (this_cie != last_cie)
+            		{
+              			last_cie = this_cie;
+              			encoding = get_cie_encoding (this_cie);
+              			base = base_from_object (encoding, ob);
+				if(getenv("EH_VERBOSE"))
+					cout<<"Base from object (mixed encoding?)="<<std::hex<<base<<endl;
+            		}
+        	}
+		
+      		if (encoding == DW_EH_PE_absptr)
+        	{
+          		//pc_begin = ((_Unwind_Ptr *) this_fde->pc_begin)[0];
+			auto my_pc_begin=(_Unwind_Ptr*)(this_fde->pc_begin);
+			memcpy(&pc_begin, my_pc_begin, sizeof(_Unwind_Ptr));
+          		//pc_range = ((_Unwind_Ptr *) this_fde->pc_begin)[1];
+			memcpy(&pc_range, my_pc_begin+1, sizeof(_Unwind_Ptr));
+
+			if(getenv("EH_VERBOSE"))
+			{
+				cout<<"absptr pc_begin 0x"<<std::hex<<(pc_begin+offset)<<"\t";
+				cout<<"absptr pc_end 0x"<<std::hex<<(pc_begin+pc_range+offset)<<endl;
+			}
+#ifndef TEST
+			extern void range(VirtualOffset_t, VirtualOffset_t);
+			range(pc_begin,pc_begin+pc_range);
+#endif
+          		if (pc_begin == 0)
+            			continue;
+        	}
+      		else
+        	{
+          		_Unwind_Ptr mask=0;
+          		unsigned char *p=0;
+		
+          		p = read_encoded_value_with_base (encoding, base,
+                                            		this_fde->pc_begin, &pc_begin);
+          		read_encoded_value_with_base (encoding & 0x0F, 0, p, &pc_range);
+
+			if(getenv("EH_VERBOSE"))
+			{
+				cout<<"!absptr pc_begin 0x"<<std::hex<<(pc_begin)<<"\t";
+				cout<<"!absptr pc_end 0x"<<std::hex<<(pc_begin+pc_range)<<endl;
+			}
+
+#ifndef TEST
+			extern void range(VirtualOffset_t, VirtualOffset_t);
+			range(pc_begin,pc_begin+pc_range);
+#endif
+
+          		/* Take care to ignore link-once functions that were removed.
+             		In these cases, the function address will be NULL, but if
+             		the encoding is smaller than a pointer a true NULL may not
+             		be representable.  Assume 0 in the representable bits is NULL.  */
+          		mask = size_of_encoded_value (encoding);
+          		if (mask < ptrsize)
+            			mask = (((_Unwind_Ptr) 1) << (mask << 3)) - 1;
+          		else
+            			mask = -1;
+		
+          		if ((pc_begin & mask) == 0)
+            			continue;
+        	}
+    	}
+
+	if(getenv("EH_VERBOSE"))
+		cout<<"Found "<<std::dec<<count<< " FDE's"<<endl;
+
+  	return;
+}
+
+void read_ehframe(FileIR_t* virp, EXEIO::exeio* exeiop)
+{
+
+	ptrsize=virp->getArchitectureBitWidth()/(8*sizeof(char));
+	// 64/8 = 8
+	// 32/8 = 4
+
+	assert(exeiop);
+	elfiop=reinterpret_cast<ELFIO::elfio*>(exeiop->get_elfio());
+	if(!elfiop)
+		return;	// skip entire analysis for non-elf files as eh-frame is way different.
+
+	const auto eh_frame_it=find_if(virp->getDataScoops().begin(), virp->getDataScoops().end(),
+		[](const DataScoop_t* scoop) { return scoop->getName()==".eh_frame"; });
+
+	// either no eh_frame in the elf file, or fill_in_indtargs removed it because
+	// it was asked to import the EH IR. 
+	if(eh_frame_it==virp->getDataScoops().end())
+		return;
+
+	int secndx=0;
+	int secnum=elfiop->sections.size(); 
+
+       	/* Locate desired section */
+       	bool found=false;
+	int eh_frame_index;
+       	for (secndx=1; secndx<secnum; secndx++)
+       	{
+		// cout<<"sechdrs["<<i<<"] name index="<<sechdrs[secndx].sh_name<<endl;
+               	const char *p=elfiop->sections[secndx]->get_name().c_str(); 
+               	if (strcmp(".eh_frame",p)==0)
+               	{
+                       	found = true;
+			eh_frame_index=secndx;
+                       	break;
+               	};
+       	}
+
+	if(!found)
+	{
+		cout<<"Cannot find .eh_frame section\n";
+		return;
+	}
+	cout<<"Found .eh_frame is section "<<std::dec<<eh_frame_index<<endl;
+
+	eh_frame_addr=(void*)elfiop->sections[eh_frame_index]->get_address();
+	cout<<"Found .eh_frame section addr is "<<std::dec<<eh_frame_addr<<endl;
+	int total_size=0;
+
+	const char *p=elfiop->sections[secndx+1]->get_name().c_str(); 
+        if (strcmp(".gcc_except_table",p)!=0)
+	{
+		cout<<"Did not find .gcc_except_table immediately after .eh_frame\n";
+		total_size=elfiop->sections[eh_frame_index]->get_size()+1;
+	}
+	else
+	{
+		total_size=
+		(elfiop->sections[eh_frame_index+1]->get_address()+
+		 elfiop->sections[eh_frame_index+1]->get_size()   ) - (uintptr_t)eh_frame_addr;
+	}
+	eh_frame_data_total_size=total_size;
+	
+	
+	// calc the size needed to safely walk the EH frame data.  apparently walking assumes a null value in memory
+	// after the section is loaded (or properly using eh_frame_hdr, which we aren't doing)
+	//eh_frame_data=(char*)elfiop->sections[eh_frame_index]->get_data();
+	int newsize=elfiop->sections[eh_frame_index]->get_size()+4;
+	eh_frame_data=(char*)calloc(1,newsize);
+	memcpy(eh_frame_data, (void*)elfiop->sections[eh_frame_index]->get_data(), elfiop->sections[eh_frame_index]->get_size());
+
+	uintptr_t offset;
+//	careful with offset and eh_offset as it can only be used for eh_frame_data offsetting, not offsetting into other addrs.
+	eh_offset=offset=(uintptr_t)eh_frame_addr-(uintptr_t)eh_frame_data;
+
+
+	struct object ob;
+	register_frame_info( eh_frame_data, &ob);
+	classify_object_over_fdes(&ob,ob.u.single);
+	linear_search_fdes (&ob,ob.u.single,offset); 
+
+	/* clean up memory */
+
+}
+
+#ifdef TEST
+//
+// main rountine; convert calls into push/jump statements 
+//
+main(int argc, char* argv[])
+{
+
+	bool fix_all=false;
+
+	if(argc!=2 && argc !=3)
+	{
+		cerr<<"Usage: fix_calls <id> (--fix-all) "<<endl;
+		exit(-1);
+	}
+
+	if(argc==3)
+	{
+		if(strcmp("--fix-all", argv[2])!=0)
+		{
+			cerr<<"Unrecognized option: "<<argv[2]<<endl;
+			exit(-1);
+		}
+		else
+			fix_all=true;
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t *virp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	cout<<"Reading variant "<<string(argv[1])<<" from database." << endl;
+	try 
+	{
+
+		pidp=new VariantID_t(atoi(argv[1]));
+
+		assert(pidp->IsRegistered()==true);
+
+		// read the db  
+		virp=new FileIR_t(*pidp);
+
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	assert(virp && pidp);
+	
+	cout<<"Reading EH frame and gcc except table in variant "<<*pidp<< "." <<endl;
+
+	read_ehframe(virp,pqxx_interface);
+
+	cout<<"Writing variant "<<*pidp<<" back to database." << endl;
+//	virp->WriteToDB();
+
+//	pqxx_interface.Commit();
+	cout<<"Done!"<<endl;
+
+	delete virp;
+	delete pidp;
+}
+#endif
diff --git a/irdb-lib/ir_builders/read_variantir.cpp b/irdb-lib/ir_builders/read_variantir.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ac24333965063027e38482406f51709aefa00cb5
--- /dev/null
+++ b/irdb-lib/ir_builders/read_variantir.cpp
@@ -0,0 +1,124 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <algorithm>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+int main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: read_variantir <id>"<<endl;
+		exit(-1);
+	}
+
+
+	VariantID_t *pidp=NULL;
+	try 
+	{
+		/* setup the interface to the sql server */
+		pqxxDB_t pqxx_interface;
+		BaseObj_t::SetInterface(&pqxx_interface);
+
+		pidp=new VariantID_t(atoi(argv[1]));
+
+		assert(pidp->IsRegistered()==true);
+
+		cout<<"New Variant, after reading registration, is: "<<*pidp << endl;
+		for(set<File_t*>::iterator it=pidp->GetFiles().begin();
+                        it!=pidp->GetFiles().end();
+                        ++it
+			)
+		{
+			File_t* this_file=*it;
+			assert(this_file);
+
+			cout<<"... Analyzing file "<<this_file->GetURL()<<endl;
+
+			// read the db  
+			FileIR_t* firp=new FileIR_t(*pidp, this_file);
+			assert(firp);
+
+			for(auto fn : firp->GetFunctions())
+				if (!fn) return;
+				cout<<"Function: " << fn->GetName();				
+				cout<<" NumArgs: " << fn->GetNumArguments();				
+				cout<<" FP: " << fn->GetUseFramePointer();				
+				cout<<" StackFrameSize: " << fn->GetStackFrameSize();				
+				cout<<" OutArgsRegionSize: " << fn->GetOutArgsRegionSize();				
+				cout<<endl;
+			};
+
+			for(
+				set<Instruction_t*>::const_iterator it=firp->GetInstructions().begin();
+				it!=firp->GetInstructions().end(); 
+				++it
+				)
+			{
+				Instruction_t* insn=*it;
+				cout<<"Found insn at addr:" << std::hex << insn->GetAddress()->GetVirtualOffset() << " " << insn->getDisassembly();
+
+				ICFS_t* ibtargets = insn->GetIBTargets();
+				if (ibtargets) 
+					cout << " ibtargets_id: " << dec << ibtargets->GetBaseID() << endl;
+				else						
+					cout << endl;
+			}
+
+			for(ICFSSet_t::const_iterator it=firp->GetAllICFS().begin();
+				it != firp->GetAllICFS().end();
+				++it)
+			{
+				ICFS_t *icfs = *it;
+				cout << "icfs set id: " << dec << icfs->GetBaseID() << " analysis status: " << icfs->GetAnalysisStatus() << "  #ibtargets: " << icfs->size() << " | ";
+				int count = 0;
+				for(ICFS_t::const_iterator it2=icfs->begin(); 
+					it2!=icfs->end(); ++it2, ++count)
+				{
+					Instruction_t* insn = *it2;
+					assert(insn);
+					cout<< std::hex << insn->GetAddress()->GetVirtualOffset() << " ";
+					if (count >= 10) {
+						cout << "...";
+						break;
+					}
+				}
+				cout << endl;
+			}
+			delete firp;
+		}
+		delete pidp;
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/ir_builders/rename_function.cpp b/irdb-lib/ir_builders/rename_function.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..4ec9fdf38b23d499a705f538b8b7396242929d0a
--- /dev/null
+++ b/irdb-lib/ir_builders/rename_function.cpp
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+void rename_function(FileIR_t* firp, string oldfn, string newfn)
+{
+
+	assert(firp);
+
+	for(
+		set<Function_t*>::iterator it=firp->GetFunctions().begin();
+		it!=firp->GetFunctions().end();
+		++it
+	   )
+	{
+		Function_t* func=*it;
+		if (!func) continue;
+		if (func->GetName() == oldfn)
+		{
+			cout<<"Renaming function " << oldfn << " to " << newfn << endl;
+			func->SetName(newfn);					
+		}
+	}
+
+	firp->WriteToDB();
+}
+
+main(int argc, char* argv[])
+{
+	if(argc!=4)
+	{
+		cerr<<"Usage: rename_function <id> <oldfn> <newfn>"<<endl;
+		exit(-1);
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t *firp=NULL;
+	string oldfn(argv[2]);
+	string newfn(argv[3]);
+
+	assert(oldfn.size() > 0 && newfn.size() > 0);
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	cout<<"Reading variant "<<string(argv[1])<<" from database." << endl;
+	try 
+	{
+		pidp=new VariantID_t(atoi(argv[1]));
+		assert(pidp->IsRegistered()==true);
+
+		for(set<File_t*>::iterator it=pidp->GetFiles().begin(); it!=pidp->GetFiles().end(); ++it)
+		{
+			File_t* this_file=*it;
+			assert(this_file);
+
+			// only do main file for now
+			if(this_file!=pidp->GetMainFile())
+				continue;
+
+			// read the db  
+			firp=new FileIR_t(*pidp,this_file);
+			
+			// rename the function
+			rename_function(firp, oldfn, newfn);
+
+			delete firp;
+		}
+		pqxx_interface.Commit();
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	cout<<"Done!"<<endl;
+
+	delete pidp;
+}
+
diff --git a/irdb-lib/ir_builders/split_eh_frame.cpp b/irdb-lib/ir_builders/split_eh_frame.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..dcd7adb752d4c5c9ab7c7d4cec0ea6d73edacf63
--- /dev/null
+++ b/irdb-lib/ir_builders/split_eh_frame.cpp
@@ -0,0 +1,630 @@
+#include <irdb-core>
+#include <iostream>
+#include <iomanip>
+#include <fstream>
+#include <limits>
+#include <stdlib.h>
+#include <string.h>
+#include <map>
+#include <assert.h>
+#include <elf.h>
+#include <algorithm>
+#include <memory>
+#include <tuple>
+#include <functional>
+
+#include <exeio.h>
+
+#include "split_eh_frame.hpp"
+#include "ehp.hpp"
+
+using namespace std;
+using namespace EXEIO;
+using namespace IRDB_SDK;
+using namespace EHP;
+
+#define ALLOF(s) begin(s), end(s)
+
+
+struct EhProgramPlaceHolder_t
+{
+	uint8_t caf;
+	int8_t daf;
+	int8_t rr;
+	uint8_t ptrsize; // needed for interpreting programs
+	IRDB_SDK::EhProgramListing_t cie_program;
+	IRDB_SDK::EhProgramListing_t fde_program;
+
+	//IRDB_SDK::EhProgramListing_t& getCIEProgram() { return cie_program; }
+	//IRDB_SDK::EhProgramListing_t& getFDEProgram() { return fde_program; }
+	const IRDB_SDK::EhProgramListing_t& getCIEProgram() const { return cie_program; }
+	const IRDB_SDK::EhProgramListing_t& getFDEProgram() const { return fde_program; }
+	uint8_t getCodeAlignmentFactor() const { return caf; } 
+	int8_t getDataAlignmentFactor() const { return daf; }
+	int8_t getReturnRegNumber() const { return rr; }
+	uint8_t getPointerSize() const { return ptrsize; }
+
+};
+
+template <int ptrsize>
+bool split_eh_frame_impl_t<ptrsize>::lsda_call_site_appliesTo(const LSDACallSite_t& cs, const Instruction_t* insn)  const
+{
+	assert(insn && insn->getAddress());
+	auto insn_addr=insn->getAddress()->getVirtualOffset();
+
+	const auto call_site_addr=cs.getCallSiteAddress();
+	const auto call_site_end_addr=cs.getCallSiteEndAddress();
+
+	return ( call_site_addr <=insn_addr && insn_addr<call_site_end_addr );
+}
+
+template <int ptrsize>
+void split_eh_frame_impl_t<ptrsize>::lsda_call_site_build_ir
+	(
+	    const LSDACallSite_t& cs,
+	    Instruction_t* insn, 
+	    const /*vector<lsda_type_table_entry_t <ptrsize> > &*/ std::shared_ptr<EHP::TypeTableVector_t> type_table_ptr, 
+	    const uint8_t& tt_encoding
+	) const
+{
+	const auto &type_table=*type_table_ptr;
+	const auto &om=offset_to_insn_map;
+	const auto landing_pad_addr=cs.getLandingPadAddress();
+	const auto action_table_ptr=cs.getActionTable();
+	const auto &action_table=*action_table_ptr;
+	assert(lsda_call_site_appliesTo(cs,insn));
+
+	// find landing pad instruction.
+	auto lp_insn=(IRDB_SDK::Instruction_t*)NULL;
+	auto lp_it=om.find(landing_pad_addr);
+	if(lp_it!=om.end())
+		lp_insn=lp_it->second;
+
+	// create the callsite.
+	auto new_ehcs = firp->addEhCallSite_t(insn, tt_encoding, lp_insn);
+
+	//cout<<"landing pad addr : 0x"<<hex<<landing_pad_addr<<endl;
+	if(action_table.size() == 0 ) 
+	{
+		new_ehcs->setHasCleanup();
+		// cout<<"Destructors to call, but no exceptions to catch"<<endl;
+	}
+	else
+	{
+		for(auto p : action_table)
+		{
+			const auto action=p->getAction();
+			if(action==0)
+			{
+				auto new_ttov=new_ehcs->getTTOrderVector();
+				new_ttov.push_back(action);
+				new_ehcs->setTTOrderVector(new_ttov);
+				//cout<<"Cleanup only (no catches) ."<<endl;
+			}
+			else if(action>0)
+			{
+				auto new_ttov=new_ehcs->getTTOrderVector();
+				new_ttov.push_back(action);
+				new_ehcs->setTTOrderVector(new_ttov);
+				// new_ehcs->getTTOrderVector().push_back(action);
+				const auto index=action - 1;
+				//cout<<"Catch for type:  ";
+				// the type table reveral was done during parsing, type table is right-side-up now.
+				//type_table.at(index).print();
+				auto wrt=(DataScoop_t*)NULL; 
+				if(type_table.at(index)->getTypeInfoPointer()!=0)
+				{
+					wrt=firp->findScoop(type_table.at(index)->getTypeInfoPointer());
+					assert(wrt);
+				}
+				const auto offset=index*type_table.at(index)->getTTEncodingSize();
+				auto addend=0;
+				if(wrt!=NULL) 
+					addend=type_table.at(index)->getTypeInfoPointer()-wrt->getStart()->getVirtualOffset();
+				/*
+				auto newreloc=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, offset, "type_table_entry", wrt, addend);
+				new_ehcs->getRelocations().insert(newreloc);
+				firp->getRelocations().insert(newreloc);
+				*/
+				auto newreloc=firp->addNewRelocation(new_ehcs,offset, "type_table_entry", wrt, addend);
+				(void)newreloc; // just give it to the ir
+
+				//if(wrt==NULL)
+				//	cout<<"Catch all in type table"<<endl;
+				//else
+				//	cout<<"Catch for type at "<<wrt->getName()<<"+0x"<<hex<<addend<<"."<<endl;
+			}
+			else if(action<0)
+			{
+				static auto already_warned=false;
+				if(!already_warned)
+				{
+					ofstream fout("warning.txt"); 
+					fout<<"Dynamic exception specification in eh_frame not fully supported."<<endl; 
+					already_warned=true;
+				}
+
+				// this isn't right at all, but pretend it's a cleanup!
+				new_ehcs->setHasCleanup();
+				//cout<<"Cleanup only (no catches) ."<<endl;
+			}
+			else
+			{
+				cout<<"What? :"<< action <<endl;
+				exit(1);
+			}
+		};
+	}
+}
+
+template <int ptrsize>
+void split_eh_frame_impl_t<ptrsize>::lsda_build_ir(const LSDA_t& lsda, Instruction_t* insn) const
+{
+	const auto  call_site_table_ptr=lsda.getCallSites();
+	const auto& call_site_table=*call_site_table_ptr;
+	const auto& type_table_ptr=lsda.getTypeTable();
+
+	const auto cs_ptr_it=find_if(ALLOF(call_site_table), [&](const shared_ptr<LSDACallSite_t> &p)
+		{
+			return lsda_call_site_appliesTo(*p, insn);
+		});
+
+	if(cs_ptr_it!= call_site_table.end())
+	{
+		const auto cs_ptr=*cs_ptr_it;
+		lsda_call_site_build_ir(*cs_ptr,insn, type_table_ptr, lsda.getTTEncoding());
+	}
+	else
+	{
+		// no call site table entry for this instruction.
+	}
+}
+
+template <int ptrsize>
+bool split_eh_frame_impl_t<ptrsize>::fde_contents_appliesTo(const FDEContents_t& fde, const Instruction_t* insn)  const
+{
+	assert(insn && insn->getAddress());
+	auto insn_addr=insn->getAddress()->getVirtualOffset();
+	const auto fde_start_addr=fde.getStartAddress();
+	const auto fde_end_addr=fde.getEndAddress();
+	return ( fde_start_addr<=insn_addr && insn_addr<fde_end_addr );
+}
+
+template <int ptrsize>
+void split_eh_frame_impl_t<ptrsize>::fde_contents_build_ir(const FDEContents_t& fde, Instruction_t* insn) const
+{
+	const auto fde_start_addr=fde.getStartAddress();
+	const auto fde_end_addr=fde.getEndAddress();
+	const auto lsda_ptr=fde.getLSDA();
+	const auto &lsda=*lsda_ptr;
+	const auto lsda_addr=fde.getLSDAAddress();
+	
+	// assert this is the right FDE.
+	assert( fde_start_addr<= insn->getAddress()->getVirtualOffset() && insn->getAddress()->getVirtualOffset() <= fde_end_addr);
+
+	//eh_pgm.print(fde_start_addr);
+	if(lsda_addr!=0)
+		lsda_build_ir(lsda,insn);
+}
+
+template <int ptrsize>
+bool split_eh_frame_impl_t<ptrsize>::init_offset_map() 
+{
+	for(const auto i : firp->getInstructions())
+	{
+		offset_to_insn_map[i->getAddress()->getVirtualOffset()]=i;
+	};
+	return false;
+}
+
+
+template <int ptrsize>
+void split_eh_frame_impl_t<ptrsize>::build_ir() const
+{
+	class whole_pgm_t
+	{
+		public:
+			whole_pgm_t(EhProgramPlaceHolder_t& _pgm, EhProgram_t* cp, uint64_t _personality)
+				: hashcode(hashPgm(_pgm)), pgm(_pgm), cached_pgm(cp), personality(_personality)
+			{
+			}
+			void setCachedProgram(EhProgram_t* cp) { cached_pgm=cp; }
+			EhProgram_t* getCachedProgram() const { return cached_pgm; }
+			uint64_t getPersonality() const { return personality; }
+		private:
+			static uint64_t hashPgm(const EhProgramPlaceHolder_t& vec)
+			{
+				auto seed = vec.getCIEProgram().size() + vec.getFDEProgram().size();
+				auto hash_fn=hash<string>();
+
+				for(const auto& i : vec.getCIEProgram()) 
+					seed ^= hash_fn(i) + 0x9e3779b9 + (seed << 6) + (seed >> 2);
+				for(const auto& i : vec.getFDEProgram()) 
+					seed ^= hash_fn(i) + 0x9e3779b9 + (seed << 6) + (seed >> 2);
+				return seed;
+			};
+		uint64_t hashcode;
+		EhProgramPlaceHolder_t pgm;
+		EhProgram_t* cached_pgm;
+		uint64_t personality;
+
+		friend struct EhProgramComparator_t;
+	};
+
+	//const auto fdes_ptr=eh_frame_parser->getFDEs();
+	//const auto &fdes=*fdes_ptr;
+
+	auto reusedpgms=size_t(0);
+	struct EhProgramComparator_t 
+	{
+		bool operator() (const whole_pgm_t& lhs, const whole_pgm_t& rhs) 
+		{
+			const auto &a=(lhs.pgm);
+			const auto &b=(rhs.pgm);
+			if(lhs.hashcode == rhs.hashcode)
+				return
+					make_tuple(
+					    a.getCIEProgram(),
+					    a.getFDEProgram(),
+					    a.getCodeAlignmentFactor(),
+					    a.getDataAlignmentFactor(),
+					    a.getReturnRegNumber(),
+					    a.getPointerSize(), 
+					    lhs.personality
+					   )
+					<
+					make_tuple(
+					    b.getCIEProgram(),
+					    b.getFDEProgram(),
+					    b.getCodeAlignmentFactor(),
+					    b.getDataAlignmentFactor(),
+					    b.getReturnRegNumber(),
+					    b.getPointerSize(), 
+					    rhs.personality
+					   );
+			else 
+				return lhs.hashcode < rhs.hashcode;
+//			return tie(*a.first, a.second) < tie(*b.first,b.second); 
+		}
+	};
+
+	// this is used to avoid adding duplicate entries to the program's IR, it allows a lookup by value
+	// instead of the IR's set which allows duplicates.
+	auto eh_program_cache = set<whole_pgm_t, EhProgramComparator_t>();
+
+	// find the right cie and fde, and build the IR from those for this instruction.
+	auto build_ir_insn=[&](Instruction_t* insn) -> void
+	{
+		const auto find_addr=insn->getAddress()->getVirtualOffset();
+		static auto fie_ptr=shared_ptr<FDEContents_t>(); 
+		static auto cie_instructions=shared_ptr<EHProgramInstructionVector_t>();
+		static auto fde_instructions=shared_ptr<EHProgramInstructionVector_t>();
+
+		if (fie_ptr && fie_ptr->getStartAddress() <= find_addr && find_addr < fie_ptr->getEndAddress())
+		{
+			// fie_ptr already points at right thing, do nothing
+		}
+		else 
+		{
+			fie_ptr=eh_frame_parser->findFDE(find_addr);
+			if(fie_ptr)
+			{
+				cie_instructions=fie_ptr->getCIE().getProgram().getInstructions();
+				fde_instructions=fie_ptr->getProgram().getInstructions();
+			}
+		}
+
+		if(fie_ptr != nullptr ) 
+		{
+			// const auto fie_ptr=*fie_ptr_it;
+
+			if(getenv("EHIR_VERBOSE")!=NULL)
+			{
+				cout<<hex<<insn->getAddress()->getVirtualOffset()<<":"
+				    <<insn->getBaseID()<<":"<<insn->getDisassembly()<<" -> "<<endl;
+				fie_ptr->print();
+			}
+
+			const auto fde_addr=fie_ptr->getStartAddress();
+			const auto caf=(uint8_t)fie_ptr->getCIE().getCAF(); 
+			const auto daf=(int8_t)fie_ptr->getCIE().getDAF(); 
+			const auto return_reg=(int8_t)fie_ptr->getCIE().getReturnRegister(); 
+			const auto personality=fie_ptr->getCIE().getPersonality(); 
+			const auto insn_addr=insn->getAddress()->getVirtualOffset();
+
+			auto import_pgm = [&](EhProgramListing_t& out_pgm_final, const shared_ptr<EHProgramInstructionVector_t> &in_pgm_instructions_ptr) -> void
+			{
+				auto out_pgm=vector<shared_ptr<EHProgramInstruction_t> >();
+				auto cur_addr=fde_addr;
+				const auto in_pgm_instructions=*in_pgm_instructions_ptr;
+				for(const auto & insn_ptr : in_pgm_instructions)
+				{
+					const auto & insn=*insn_ptr;
+					if(insn.advance(cur_addr, caf))
+					{	
+						if(cur_addr > insn_addr)
+							break;
+					}
+					else if(insn.isNop())
+					{
+						// skip nops 
+					}
+					else if(insn.isRestoreState())
+					{
+						// if a restore state happens, pop back out any instructions until
+						// we find the corresponding remember_state
+						while(1)
+						{
+							if(out_pgm.size()==0)
+							{
+								// unmatched remember state
+								cerr<<"Error in CIE/FDE program:  unmatched restore_state command"<<endl;
+								break;
+							}
+							const auto back_insn=out_pgm.back();
+							out_pgm.pop_back();
+							//const auto back_insn=eh_program_insn_t<ptrsize>(back_str);
+							if(back_insn->isRememberState())
+								break;
+						}
+					}
+					else
+					{
+						out_pgm.push_back(insn_ptr);
+					}
+
+				}
+				if(getenv("EHIR_VERBOSE")!=NULL)
+				{
+					cout<<"\tPgm has insn_count="<<out_pgm.size()<<endl;
+				}
+				transform
+				    (
+				        ALLOF(out_pgm), 
+				        back_inserter(out_pgm_final), 
+				        [](const shared_ptr<EHProgramInstruction_t>& p){ return string(ALLOF(p->getBytes()));}
+				    ); 
+			}; 
+
+
+			// build an eh program on the stack;
+			//
+			auto ehpgm=EhProgramPlaceHolder_t({caf,daf,return_reg, ptrsize, {}, {}});
+			import_pgm(ehpgm.cie_program, cie_instructions);
+			import_pgm(ehpgm.fde_program, fde_instructions);
+
+
+			//if(getenv("EHIR_VERBOSE")!=NULL)
+			//	ehpgm.print();
+			// see if we've already built this one.
+			auto ehpgm_it = eh_program_cache.find(whole_pgm_t(ehpgm, nullptr, personality)) ;
+			if(ehpgm_it != eh_program_cache.end())
+			{
+				// yes, use the cached program.
+				insn->setEhProgram(ehpgm_it->getCachedProgram());
+				if(getenv("EHIR_VERBOSE")!=NULL)
+					cout<<"Re-using existing Program!"<<endl;
+				reusedpgms++;
+			}
+			else /* doesn't yet exist! */
+			{
+				
+				if(getenv("EHIR_VERBOSE")!=NULL)
+					cout<<"Allocating new Program!"<<endl;
+
+				// allocate a new pgm in the heap so we can give it to the IR.
+				/*
+				auto newehpgm=new EhProgram_t(ehpgm); // copy constructor
+				assert(newehpgm);
+				firp->getAllEhPrograms().insert(newehpgm);
+				insn->setEhProgram(newehpgm);
+				*/
+				auto newehpgm=firp->addEhProgram(insn, ehpgm.caf, ehpgm.daf,ehpgm.rr, ehpgm.ptrsize, ehpgm.cie_program, ehpgm.fde_program);
+
+				// allocate a relocation for the personality and give it to the IR.	
+				auto personality_scoop=firp->findScoop(personality);
+				auto personality_insn_it=offset_to_insn_map.find(personality);
+				auto personality_insn=personality_insn_it==offset_to_insn_map.end() ? (Instruction_t*)NULL : personality_insn_it->second;
+				auto personality_obj = personality_scoop ? (BaseObj_t*)personality_scoop : (BaseObj_t*)personality_insn;
+				auto addend= personality_scoop ? personality - personality_scoop->getStart()->getVirtualOffset() : 0;
+				assert(personality==0 || personality_obj!=NULL);
+
+				if(personality_obj==NULL)
+				{
+					if(getenv("EHIR_VERBOSE")!=NULL)
+						cout<<"Null personality obj: 0x"<<hex<<personality<<endl;
+				}
+				else if(personality_scoop)
+				{
+					if(getenv("EHIR_VERBOSE")!=NULL)
+						cout<<"Found personality scoop: 0x"<<hex<<personality<<" -> "
+						    <<personality_scoop->getName()<<"+0x"<<hex<<addend<<endl;
+				}
+				else if(personality_insn)
+				{
+					if(getenv("EHIR_VERBOSE")!=NULL)
+						cout<<"Found personality insn: 0x"<<hex<<personality<<" -> "
+						    <<personality_insn->getBaseID()<<":"<<personality_insn->getDisassembly()<<endl;
+				}
+				else
+					assert(0);
+
+				/*
+				auto newreloc=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, 0, "personality", personality_obj, addend);
+				assert(newreloc);	
+				newehpgm->getRelocations().insert(newreloc);
+				firp->getRelocations().insert(newreloc);
+				*/
+				auto newreloc=firp->addNewRelocation(newehpgm,0, "personality", personality_obj, addend);
+				(void)newreloc; // not used, just give it to the IR
+
+				// update cache.
+				eh_program_cache.insert( whole_pgm_t(ehpgm,newehpgm,personality));
+			}
+			
+			// build the IR from the FDE.
+			fde_contents_build_ir(*fie_ptr.get(), insn);
+		}
+		else
+		{
+			if(getenv("EHIR_VERBOSE")!=NULL)
+			{
+				cout<<hex<<insn->getAddress()->getVirtualOffset()<<":"
+				    <<insn->getBaseID()<<":"<<insn->getDisassembly()<<" has no FDE "<<endl;
+			}
+		}
+		
+	};
+
+#if 0
+	auto remove_reloc=[&](Relocation_t* r) -> void
+	{
+		firp->getRelocations().erase(r);
+		delete r;
+	};
+
+	auto remove_address=[&](AddressID_t* a) -> void
+	{
+		firp->getAddresses().erase(a);
+		for(auto &r : a->getRelocations()) remove_reloc(r);
+		for(auto &r : firp->getRelocations()) assert(r->getWRT() != a);
+		delete a;	
+	};
+
+	auto remove_scoop=[&] (DataScoop_t* s) -> void 
+	{ 
+		if(s==NULL)
+			return;
+		firp->getDataScoops().erase(s);
+		remove_address(s->getStart());
+		remove_address(s->getEnd());
+		for(auto &r : s->getRelocations()) remove_reloc(r);
+		for(auto &r : firp->getRelocations()) assert(r->getWRT() != s);
+		delete s;
+	};
+#endif
+
+	for(Instruction_t* i : firp->getInstructions())
+	{
+		build_ir_insn(i);
+	}
+
+	cout<<"# ATTRIBUTE Split_Exception_Handler::total_eh_programs_created="<<dec<<firp->getAllEhPrograms().size()<<endl;
+	cout<<"# ATTRIBUTE Split_Exception_Handler::total_eh_programs_reused="<<dec<<reusedpgms<<endl;
+	cout<<"# ATTRIBUTE Split_Exception_Handler::total_eh_programs="<<dec<<firp->getAllEhPrograms().size()+reusedpgms<<endl;
+	cout<<"# ATTRIBUTE Split_Exception_Handler::pct_eh_programs="<<std::fixed
+	    <<((float)firp->getAllEhPrograms().size()/((float)firp->getAllEhPrograms().size()+reusedpgms))*100.00
+	    <<"%" <<endl;
+	cout<<"# ATTRIBUTE Split_Exception_Handler::pct_eh_programs_reused="<<std::fixed
+	    <<((float)reusedpgms/((float)firp->getAllEhPrograms().size()+reusedpgms))*100.00
+	    <<"%"<<endl;
+
+	firp->removeScoop(eh_frame_scoop);
+	firp->removeScoop(eh_frame_hdr_scoop);
+	firp->removeScoop(gcc_except_table_scoop);
+
+}
+
+template <int ptrsize>
+Instruction_t* split_eh_frame_impl_t<ptrsize>::find_lp(Instruction_t* i) const 
+{
+	const auto find_addr=i->getAddress()->getVirtualOffset();
+	const auto fde_ptr=eh_frame_parser->findFDE(find_addr);
+
+	if(fde_ptr==nullptr)
+		return nullptr;
+
+	const auto &the_fde=*fde_ptr;
+	const auto &the_lsda_ptr=the_fde.getLSDA();
+	const auto &the_lsda=*the_lsda_ptr;
+	const auto &cstab_ptr  = the_lsda.getCallSites();
+	const auto &cstab  = *cstab_ptr;
+
+	const auto cstab_it=find_if(ALLOF(cstab), [&](const shared_ptr<LSDACallSite_t>& cs)
+		{ return lsda_call_site_appliesTo(*cs,i); });
+
+	if(cstab_it==cstab.end())
+		return nullptr;
+
+	const auto &the_cstab_entry_ptr=*cstab_it;
+	const auto &the_cstab_entry=*the_cstab_entry_ptr;
+	const auto lp_addr= the_cstab_entry.getLandingPadAddress();
+
+	const auto om_it=offset_to_insn_map.find(lp_addr);
+
+	if(om_it==offset_to_insn_map.end())
+		return nullptr;
+
+	auto lp=om_it->second;
+	return lp;
+}
+
+template <int ptrsize>
+void split_eh_frame_impl_t<ptrsize>::print() const
+{
+	eh_frame_parser->print();
+}
+
+template <int ptrsize>
+split_eh_frame_impl_t<ptrsize>::split_eh_frame_impl_t(FileIR_t* p_firp)
+	: firp(p_firp),
+	  eh_frame_scoop(NULL),
+	  eh_frame_hdr_scoop(NULL),
+	  gcc_except_table_scoop(NULL)
+{
+	assert(firp!=NULL);
+
+	// function to find a scoop by name.
+	auto lookup_scoop_by_name=[&](const string &the_name) -> DataScoop_t* 
+	{
+		const auto scoop_it=find_if(
+			firp->getDataScoops().begin(), 
+			firp->getDataScoops().end(), 
+			[the_name](DataScoop_t* scoop)
+			{
+				return scoop->getName()==the_name;
+			});
+
+		if(scoop_it!=firp->getDataScoops().end())
+			return *scoop_it;
+		return NULL;
+	};
+	auto scoop_address=[&](const DataScoop_t* p) -> uint64_t { return p==NULL ? 0  : p->getStart()->getVirtualOffset(); };
+	auto scoop_contents=[&](const DataScoop_t* p) -> string  { return p==NULL ? "" : p->getContents(); };
+
+	eh_frame_scoop=lookup_scoop_by_name(".eh_frame");
+	eh_frame_hdr_scoop=lookup_scoop_by_name(".eh_frame_hdr");
+	gcc_except_table_scoop=lookup_scoop_by_name(".gcc_except_table");
+
+	eh_frame_parser=EHFrameParser_t::factory
+		( 
+		    ptrsize,
+		    scoop_contents(eh_frame_scoop),         scoop_address(eh_frame_scoop), 
+		    scoop_contents(eh_frame_hdr_scoop),     scoop_address(eh_frame_hdr_scoop), 
+		    scoop_contents(gcc_except_table_scoop), scoop_address(gcc_except_table_scoop)
+		);
+
+	if(eh_frame_parser!=NULL)
+		fdes=eh_frame_parser->getFDEs();
+
+	(void)init_offset_map();
+}
+
+unique_ptr<split_eh_frame_t> split_eh_frame_t::factory(FileIR_t *firp)
+{
+	if( firp->getArchitectureBitWidth()==64)
+		return unique_ptr<split_eh_frame_t>(new split_eh_frame_impl_t<8>(firp));
+	else
+		return unique_ptr<split_eh_frame_t>(new split_eh_frame_impl_t<4>(firp));
+
+}
+
+void split_eh_frame(FileIR_t* firp)
+{
+	auto found_err=false;
+	//auto eh_frame_splitter=(unique_ptr<split_eh_frame_t>)NULL;
+	const auto eh_frame_splitter=split_eh_frame_t::factory(firp);
+	eh_frame_splitter->build_ir();
+
+	assert(!found_err);
+}
diff --git a/irdb-lib/ir_builders/split_eh_frame.hpp b/irdb-lib/ir_builders/split_eh_frame.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..2e1a2b08eb507eb17a802009b8033e6cb31d887f
--- /dev/null
+++ b/irdb-lib/ir_builders/split_eh_frame.hpp
@@ -0,0 +1,95 @@
+#ifndef eh_frame_hpp
+#define eh_frame_hpp
+
+#include <irdb-core>
+#include <iostream>
+#include <iomanip>
+#include <fstream>
+#include <limits>
+#include <stdlib.h>
+#include <string.h>
+#include <map>
+#include <assert.h>
+#include <elf.h>
+#include <algorithm>
+#include <memory>
+
+#include <exeio.h>
+#include <ehp.hpp>
+
+
+
+
+using OffsetMap_t = std::map<IRDB_SDK::VirtualOffset_t, IRDB_SDK::Instruction_t*>;
+
+class split_eh_frame_t 
+{
+	public:
+
+		virtual void build_ir() const =0;
+		virtual void print() const=0;
+		virtual IRDB_SDK::Instruction_t* find_lp(IRDB_SDK::Instruction_t*) const =0;
+
+		static std::unique_ptr<split_eh_frame_t> factory(IRDB_SDK::FileIR_t *firp);
+
+};
+
+template <int ptrsize>
+class split_eh_frame_impl_t : public split_eh_frame_t
+{
+	private: 
+
+	IRDB_SDK::FileIR_t* firp;
+	IRDB_SDK::DataScoop_t* eh_frame_scoop;
+	IRDB_SDK::DataScoop_t* eh_frame_hdr_scoop;
+	IRDB_SDK::DataScoop_t* gcc_except_table_scoop;
+	OffsetMap_t offset_to_insn_map;
+
+	std::unique_ptr<const EHP::EHFrameParser_t> eh_frame_parser;
+	std::shared_ptr<const EHP::FDEVector_t> fdes;
+
+	bool init_offset_map();
+
+	bool lsda_call_site_appliesTo
+		(
+		    const EHP::LSDACallSite_t& cs, 
+		    const IRDB_SDK::Instruction_t* insn
+		) const;
+	void lsda_call_site_build_ir
+		(
+		    const EHP::LSDACallSite_t& cs,
+		    IRDB_SDK::Instruction_t* insn, 
+		    /* const std::vector<lsda_type_table_entry_t <ptrsize> > &*/ std::shared_ptr<EHP::TypeTableVector_t> type_table_ptr, 
+		    const uint8_t& tt_encoding
+		) const;
+	void lsda_build_ir
+		(
+		    const EHP::LSDA_t& lsda,
+		    IRDB_SDK::Instruction_t* insn
+		) const;
+        bool fde_contents_appliesTo
+		(
+		    const EHP::FDEContents_t& fde,
+		    const IRDB_SDK::Instruction_t* insn
+		) const;
+	void fde_contents_build_ir
+		(
+		    const EHP::FDEContents_t& fde,
+		    IRDB_SDK::Instruction_t* insn
+		) const;
+
+	public:
+
+	split_eh_frame_impl_t(IRDB_SDK::FileIR_t* p_firp);
+
+
+	void print() const;
+
+	void build_ir() const;
+
+	IRDB_SDK::Instruction_t* find_lp(IRDB_SDK::Instruction_t*) const ;
+};
+
+void split_eh_frame(IRDB_SDK::FileIR_t* firp);
+
+#endif
diff --git a/irdb-lib/ir_builders/tests/ibtarget/Makefile b/irdb-lib/ir_builders/tests/ibtarget/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..3b0ad3b1ac0436e951c1793ca7c4d21f4db9eb67
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/Makefile
@@ -0,0 +1,38 @@
+INCLUDES= -I../../../../include -I../../../include/ -I../../../../beaengine/include 
+#LIBS=-L ../../../lib/ -lIRDB-core -lIRDB-cfg -lIRDB-util -lpqxx -L ../../../../beaengine/lib/Linux.gnu.Debug -lBeaEngine_s_d 
+#OPT=-fPIE -fPIC -O
+#OPT=-g -fPIE -fPIC
+OPT=-O
+.SUFFIXES: .exe .cpp .protected
+
+PROGS=jmp1.exe jmp2.exe jmp.shared.exe icall.exe
+PEASOUP_PROGS=jmp1.protected jmp2.protected jmp.shared.protected icall.protected
+
+all: $(PROGS)
+protected: $(PEASOUP_PROGS)
+
+$(PROGS): ../../../../lib/*
+
+.exe.protected: $<
+#	FIX_CALLS_FIX_ALL_CALLS=1 LD_LIBRARY_PATH="$(LD_LIBRARY_PATH):." $(PEASOUP_HOME)/tools/ps_analyze.sh $< $@ --backend zipr --step selective_cfi=on 
+#	FIX_CALLS_FIX_ALL_CALLS=1 LD_LIBRARY_PATH="$(LD_LIBRARY_PATH):." $(PEASOUP_HOME)/tools/ps_analyze.sh $< $@ --backend zipr --step selective_cfi=on --step-option selective_cfi:--color
+	FIX_CALLS_FIX_ALL_CALLS=1 LD_LIBRARY_PATH="$(LD_LIBRARY_PATH):." $(PEASOUP_HOME)/tools/ps_analyze.sh $< $@ --backend zipr 
+#	LD_LIBRARY_PATH="$(LD_LIBRARY_PATH):." $(PEASOUP_HOME)/tools/ps_analyze.sh $< $@ --backend zipr --stop_after pdb_register
+
+.o.exe:  $< ../lib/libIRDB-core.a ../lib/libIRDB-cfg.a
+	g++ $< $(INCLUDES) $(LIBS) $(OPT)  -o $@
+
+.cpp.o:  $< 
+	g++ $< $(INCLUDES) $(LIBS) $(OPT) -o $@ -c
+
+jmp.shared.so: jmp.shared.cpp jmp2.shared.cpp
+	g++ -fPIC -c jmp.shared.cpp
+	g++ -fPIC -c jmp2.shared.cpp
+	g++ -shared -Wl,-soname,libjmp.so -o libjmp.so jmp.shared.o jmp2.shared.o
+
+jmp.shared.exe: jmp.shared.so jmp.main.cpp
+	g++ -c jmp.main.cpp
+	g++ jmp.main.o -L. -ljmp -o $@
+
+clean:
+	rm -fr $(PROGS) *.o *.so peasoup_executable* *.protected *.tmp.orig 
diff --git a/irdb-lib/ir_builders/tests/ibtarget/README b/irdb-lib/ir_builders/tests/ibtarget/README
new file mode 100644
index 0000000000000000000000000000000000000000..4e563b9edb039d8ecd20f094b554d1f534c1a7f2
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/README
@@ -0,0 +1,21 @@
+to test:
+
+[x] 32,nonPIC,nonOptimized
+[x] 32,nonPIC,optimized
+[x] 32,PIC,nonOptimized
+[x] 32,PIC,optimized
+[x] 32,shared lib, nonOpt
+[x] 32,shared lib, optimized
+[x] verify GetIBTargets() off Instruction_t*
+
+[x] 64,nonPIC,nonOptimized
+[x] 64,nonPIC,optimized
+[x] 64,PIC,nonOptimized
+[x] 64,PIC,optimized
+[x] 64,shared lib, nonOpt
+[x] 64,shared lib, optimized
+[x] verify GetIBTargets() off Instruction_t*
+
+[ ] make sure fix_calls copies the indirect branch targets
+[ ] induce head-merge, and tail-merge in switch case
+
diff --git a/irdb-lib/ir_builders/tests/ibtarget/icall.cpp b/irdb-lib/ir_builders/tests/ibtarget/icall.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..41c87bad0c97fe4a223de3a80b6b31ca068d62a3
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/icall.cpp
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+
+int add(int a, int b)
+{
+	printf("%d + %d = %d\n", a, b, a+b);
+	return a + b;
+}
+
+int sub(int a, int b)
+{
+	printf("%d - %d = %d\n", a, b, a-b);
+	return a - b;
+}
+
+int mul(int a, int b)
+{
+	printf("%d * %d = %d\n", a, b, a*b);
+	return a * b;
+}
+
+int main(int argc, char**argv)
+{
+	int (*fn)(int,int);
+
+	if (argc % 2)
+		fn = &add;
+	else
+		fn = &sub;
+
+	int result = (*fn)(argc, argc+1);
+	printf("result = %d\n", result);
+}
diff --git a/irdb-lib/ir_builders/tests/ibtarget/jmp.main.cpp b/irdb-lib/ir_builders/tests/ibtarget/jmp.main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..bf97bed9c68359a174efe9641c777e8994303d49
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/jmp.main.cpp
@@ -0,0 +1,31 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdio.h>
+
+extern int switch_table(int, char**);
+extern int switch_table_2(int, char**);
+
+int main(int argc, char** argv)
+{
+	printf("testing switch tables in shared library\n");
+	switch_table(argc, argv);
+	switch_table_2(argc, argv);
+}
diff --git a/irdb-lib/ir_builders/tests/ibtarget/jmp.shared.cpp b/irdb-lib/ir_builders/tests/ibtarget/jmp.shared.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..eccfeb5e892431dcd1109f769e7ca2415aedcab5
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/jmp.shared.cpp
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+int add(int a, int b)
+{
+	int x = a + b;
+	printf("add(): %d + %d = %d\n", a, b, x);
+	return x;
+}
+
+int switch_table(int argc, char **argv)
+{
+	int i = atoi(argv[1]);
+
+	switch(i) 
+	{
+		case 20:
+			printf("i = 20\n");
+			break;
+		case 22:
+			printf("i = 22\n");
+			break;
+		case 23:
+			printf("hello: ");
+			printf("i = 23\n");
+			break;
+		case 24:
+			printf("i = 24\n");
+			break;
+		case 25:
+			printf("i = 25\n");
+			break;
+		case 26:
+			printf("bar: ");
+			printf("i = 26\n");
+			break;
+		case 27:
+			printf("i = 27\n");
+			break;
+		case 28:
+			printf("i = 28\n");
+			break;
+		default:
+			printf("i = %d\n", i);
+	}
+
+	int val = add(i,i);
+	printf("main(): %d + %d = %d\n", i, i, val);
+}
diff --git a/irdb-lib/ir_builders/tests/ibtarget/jmp1.cpp b/irdb-lib/ir_builders/tests/ibtarget/jmp1.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..aa11e16c0aeff900b190724195f0194cc09311aa
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/jmp1.cpp
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+int add(int a, int b)
+{
+	int x = a + b;
+	printf("add(): %d + %d = %d\n", a, b, x);
+	return x;
+}
+
+int main(int argc, char **argv)
+{
+	int i = atoi(argv[1]);
+
+	switch(i) 
+	{
+		case 20:
+			printf("i = 20\n");
+			break;
+		case 22:
+			printf("i = 22\n");
+			break;
+		case 23:
+			printf("hello: ");
+			printf("i = 23\n");
+			break;
+		case 24:
+			printf("i = 24\n");
+			break;
+		case 25:
+			printf("i = 25\n");
+			break;
+		case 26:
+			printf("bar: ");
+			printf("i = 26\n");
+			break;
+		case 27:
+			printf("i = 27\n");
+			break;
+		case 28:
+			printf("i = 28\n");
+			break;
+		default:
+			printf("i = %d\n", i);
+	}
+
+	int val = add(i,i);
+	printf("main(): %d + %d = %d\n", i, i, val);
+}
diff --git a/irdb-lib/ir_builders/tests/ibtarget/jmp2.cpp b/irdb-lib/ir_builders/tests/ibtarget/jmp2.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..83244e7f2d070a00c8abb0a692d049afec214415
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/jmp2.cpp
@@ -0,0 +1,117 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+int add(int a, int b)
+{
+	int x = a + b;
+	printf("add(): %d + %d = %d\n", a, b, x);
+	return x;
+}
+
+int main(int argc, char **argv)
+{
+	int i = atoi(argv[1]);
+
+	switch(i) 
+	{
+		case 20:
+			printf("i = 20\n");
+			break;
+		case 22:
+			printf("i = 22\n");
+			break;
+		case 23:
+			printf("hello: ");
+			printf("i = 23\n");
+			break;
+		case 24:
+			printf("i = 24\n");
+			break;
+		case 25:
+			printf("i = 25\n");
+			break;
+		case 26:
+			printf("bar: ");
+			printf("i = 26\n");
+			break;
+		case 27:
+			printf("i = 27\n");
+			break;
+		case 28:
+			printf("i = 28\n");
+			break;
+		default:
+			printf("i = %d\n", i);
+	}
+
+	int val = add(i,i);
+	printf("main(): %d + %d = %d\n", i, i, val);
+
+	switch(val) 
+	{
+		case 20:
+			val = 35;
+			printf("a\n");
+			break;
+		case 22:
+			val = add(21,31);
+			printf("36\n");
+			break;
+		case 23:
+			val = add(val, val);
+			printf("37\n");
+			break;
+		case 24:
+			val = add(val, 34);
+			printf("38\n");
+			break;
+		case 25:
+			val = 38;
+			printf("39\n");
+			break;
+		case 26:
+			val = 45;
+			printf("45\n");
+			break;
+		case 27:
+			val = 55;
+			printf("55\n");
+			break;
+		case 28:
+			val = 69;
+			printf("69\n");
+			break;
+		case 29:
+			val = 72;
+			break;
+		case 31:
+			val = 82;
+			printf("82\n");
+			break;
+		default:
+			val = 99;
+	}
+
+	printf("val = %d\n", val);
+
+}
diff --git a/irdb-lib/ir_builders/tests/ibtarget/jmp2.shared.cpp b/irdb-lib/ir_builders/tests/ibtarget/jmp2.shared.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a6bb2d9fce89013d28087b66c8e1e898e485bb82
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/jmp2.shared.cpp
@@ -0,0 +1,112 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+extern int add(int, int);
+
+int switch_table_2(int argc, char **argv)
+{
+	int i = atoi(argv[1]);
+
+	switch(i) 
+	{
+		case 20:
+			printf("i = 20\n");
+			break;
+		case 22:
+			printf("i = 22\n");
+			break;
+		case 23:
+			printf("hello: ");
+			printf("i = 23\n");
+			break;
+		case 24:
+			printf("i = 24\n");
+			break;
+		case 25:
+			printf("i = 25\n");
+			break;
+		case 26:
+			printf("bar: ");
+			printf("i = 26\n");
+			break;
+		case 27:
+			printf("i = 27\n");
+			break;
+		case 28:
+			printf("i = 28\n");
+			break;
+		default:
+			printf("i = %d\n", i);
+	}
+
+	int val = add(i,i);
+	printf("main(): %d + %d = %d\n", i, i, val);
+
+	switch(val) 
+	{
+		case 20:
+			val = 35;
+			printf("a\n");
+			break;
+		case 22:
+			val = add(21,31);
+			printf("36\n");
+			break;
+		case 23:
+			val = add(val, val);
+			printf("37\n");
+			break;
+		case 24:
+			val = add(val, 34);
+			printf("38\n");
+			break;
+		case 25:
+			val = 38;
+			printf("39\n");
+			break;
+		case 26:
+			val = 45;
+			printf("45\n");
+			break;
+		case 27:
+			val = 55;
+			printf("55\n");
+			break;
+		case 28:
+			val = 69;
+			printf("69\n");
+			break;
+		case 29:
+			val = 72;
+			break;
+		case 31:
+			val = 82;
+			printf("82\n");
+			break;
+		default:
+			val = 99;
+	}
+
+	printf("val = %d\n", val);
+
+}
diff --git a/irdb-lib/ir_builders/tests/ibtarget/validate_ibts.sh b/irdb-lib/ir_builders/tests/ibtarget/validate_ibts.sh
new file mode 100755
index 0000000000000000000000000000000000000000..f95b2cd9d31c532561d403ac2000b9411c94c28e
--- /dev/null
+++ b/irdb-lib/ir_builders/tests/ibtarget/validate_ibts.sh
@@ -0,0 +1,38 @@
+# build original and protected test programs
+make clean all protected
+if [ ! $? -eq 0 ]; then
+	echo "failed to compile test programs"
+	exit 1
+fi
+
+export LD_LIBRARY_PATH="${LD_LIBRARY_PATH}:."
+
+ALL_PASS_STATUS=0
+# compare output
+for i in `ls *.exe`
+do
+	orig=$i
+	base=$(basename $orig .exe)
+	protected=${base}.protected
+
+	echo $orig $base $protected
+	./$orig 1 2 > $$.tmp.orig
+	./$protected 1 2 > $$.tmp.protected
+	diff $$.tmp.orig $$.tmp.protected
+	if [ ! $? -eq 0 ]; then
+		echo "FAIL: Protected program ${base}.protected does not match original program"
+		ALL_PASS_STATUS=1
+	else
+		echo "PASS: $orig vs. $protected"
+	fi
+
+	rm $$.tmp.orig $$.tmp.protected
+done
+
+echo
+if [ $ALL_PASS_STATUS -eq 0 ]; then
+	echo "PASS: all tests passed"
+else
+	echo "FAIL: one or more test failed"
+fi
+
diff --git a/irdb-lib/ir_builders/unfix_calls.cpp b/irdb-lib/ir_builders/unfix_calls.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..65ed56dfa103341f771dc2d7fdc14e8ee4d6d47a
--- /dev/null
+++ b/irdb-lib/ir_builders/unfix_calls.cpp
@@ -0,0 +1,154 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <libIRDB-core.hpp>
+#include <libIRDB-cfg.hpp>
+#include <iostream>
+#include <stdlib.h>
+#include <assert.h>
+#include <string.h>
+
+
+
+using namespace libIRDB;
+using namespace std;
+
+void unfix_call(Instruction_t* insn, FileIR_t *virp);
+bool is_push(Instruction_t* insn);
+
+void unfix_calls(FileIR_t* virp)
+{
+	for(
+		set<Instruction_t*>::const_iterator it=virp->GetInstructions().begin();
+		it!=virp->GetInstructions().end(); 
+		++it
+	   )
+	{
+
+		Instruction_t* insn=*it;
+		unfix_call(insn, virp);
+	}
+}
+
+void unfix_call(Instruction_t* insn, FileIR_t *virp)
+{
+	/* we need a push instruction */
+	assert(insn);
+	if(!is_push(insn))
+		return;
+	/* that has a fallthrough */
+	Instruction_t* nextinsn=insn->GetFallthrough();
+	if(!nextinsn)
+		return;
+
+	/* to a jump */
+	Instruction_t* target=nextinsn->GetTarget();
+	if(!target)
+		return;
+
+	/* that isn't conditional */
+	Instruction_t* fallthrough=nextinsn->GetFallthrough();
+	if(fallthrough)
+		return;
+
+	/* and the target has a function */
+	Function_t *target_func=target->GetFunction();
+	if(!target_func)
+		return;
+
+	/* more checks?  that the value pushed is an original program address?  and one that originally follows the call? */
+
+	/* it seems that this instruction has met its prereqs. for converting to a call*/ 
+	ControlFlowGraph_t *target_cfg=new ControlFlowGraph_t(target_func);
+
+	cout<<"Built CFG for func "<< target_func->GetName() << endl;
+
+	cout<<*target_cfg<<endl;
+
+	/* cleanup */
+	delete target_cfg;
+
+}
+
+
+//
+// return true if insn is a call
+//
+bool is_push(Instruction_t* insn)
+{
+	return insn->GetDataBits()[0]==0x68;
+}
+
+
+//
+// main rountine; convert calls into push/jump statements 
+//
+main(int argc, char* argv[])
+{
+
+	if(argc!=2)
+	{
+		cerr<<"Usage: ilr <id>"<<endl;
+		exit(-1);
+	}
+
+	VariantID_t *pidp=NULL;
+	FileIR_t *virp=NULL;
+
+	/* setup the interface to the sql server */
+	pqxxDB_t pqxx_interface;
+	BaseObj_t::SetInterface(&pqxx_interface);
+
+	cout<<"Reading variant "<<string(argv[1])<<" from database." << endl;
+	try 
+	{
+
+		pidp=new VariantID_t(atoi(argv[1]));
+
+		assert(pidp->IsRegistered()==true);
+
+		// read the db  
+		virp=new FileIR_t(*pidp);
+
+
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cout<<"Unexpected database error: "<<pnide<<endl;
+		exit(-1);
+        }
+
+	assert(virp && pidp);
+
+	cout<<"Adjusting push/jmp -> call in variant "<<*pidp<< "." <<endl;
+	
+	unfix_calls(virp);
+
+	cout<<"Writing variant "<<*pidp<<" back to database." << endl;
+	virp->WriteToDB();
+
+	pqxx_interface.Commit();
+	cout<<"Done!"<<endl;
+
+	delete virp;
+	delete pidp;
+}
diff --git a/irdb-lib/ir_builders/unwind-pe.h b/irdb-lib/ir_builders/unwind-pe.h
new file mode 100644
index 0000000000000000000000000000000000000000..a3c41963ff4bc878fe7492bccf2b766cf8246ca6
--- /dev/null
+++ b/irdb-lib/ir_builders/unwind-pe.h
@@ -0,0 +1,313 @@
+/* Exception handling and frame unwind runtime interface routines.
+   Copyright (C) 2001, 2002, 2003, 2004, 2008, 2009 Free Software Foundation, Inc.
+
+   This file is part of GCC.
+
+   GCC is free software; you can redistribute it and/or modify it
+   under the terms of the GNU General Public License as published by
+   the Free Software Foundation; either version 3, or (at your option)
+   any later version.
+
+   GCC is distributed in the hope that it will be useful, but WITHOUT
+   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+   or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
+   License for more details.
+
+   Under Section 7 of GPL version 3, you are granted additional
+   permissions described in the GCC Runtime Library Exception, version
+   3.1, as published by the Free Software Foundation.
+
+   You should have received a copy of the GNU General Public License and
+   a copy of the GCC Runtime Library Exception along with this program;
+   see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
+   <http://www.gnu.org/licenses/>.  */
+
+/* @@@ Really this should be out of line, but this also causes link
+   compatibility problems with the base ABI.  This is slightly better
+   than duplicating code, however.  */
+
+#ifndef GCC_UNWIND_PE_H
+#define GCC_UNWIND_PE_H
+
+/* If using C++, references to abort have to be qualified with std::.  */
+#if __cplusplus
+#define __gxx_abort std::abort
+#else
+#define __gxx_abort abort
+#endif
+
+/* Pointer encodings, from dwarf2.h.  */
+#define DW_EH_PE_absptr         0x00
+#define DW_EH_PE_omit           0xff
+
+#define DW_EH_PE_uleb128        0x01
+#define DW_EH_PE_udata2         0x02
+#define DW_EH_PE_udata4         0x03
+#define DW_EH_PE_udata8         0x04
+#define DW_EH_PE_sleb128        0x09
+#define DW_EH_PE_sdata2         0x0A
+#define DW_EH_PE_sdata4         0x0B
+#define DW_EH_PE_sdata8         0x0C
+#define DW_EH_PE_signed         0x08
+
+#define DW_EH_PE_pcrel          0x10
+#define DW_EH_PE_textrel        0x20
+#define DW_EH_PE_datarel        0x30
+#define DW_EH_PE_funcrel        0x40
+#define DW_EH_PE_aligned        0x50
+
+#define DW_EH_PE_indirect	0x80
+
+
+#ifndef NO_SIZE_OF_ENCODED_VALUE
+
+/* Given an encoding, return the number of bytes the format occupies.
+   This is only defined for fixed-size encodings, and so does not
+   include leb128.  */
+
+static unsigned int
+size_of_encoded_value (unsigned char encoding) __attribute__ ((unused));
+
+static unsigned int
+size_of_encoded_value (unsigned char encoding)
+{
+  if (encoding == DW_EH_PE_omit)
+    return 0;
+
+  switch (encoding & 0x07)
+    {
+    case DW_EH_PE_absptr:
+      return ptrsize;
+    case DW_EH_PE_udata2:
+      return 2;
+    case DW_EH_PE_udata4:
+      return 4;
+    case DW_EH_PE_udata8:
+      return 8;
+    }
+  __gxx_abort ();
+}
+
+#endif
+
+#ifndef NO_BASE_OF_ENCODED_VALUE
+
+/* Given an encoding and an _Unwind_Context, return the base to which
+   the encoding is relative.  This base may then be passed to
+   read_encoded_value_with_base for use when the _Unwind_Context is
+   not available.  */
+
+static _Unwind_Ptr
+base_of_encoded_value (unsigned char encoding, struct _Unwind_Context *context)
+{
+  if (encoding == DW_EH_PE_omit)
+    return 0;
+
+  switch (encoding & 0x70)
+    {
+    case DW_EH_PE_absptr:
+    case DW_EH_PE_pcrel:
+    case DW_EH_PE_aligned:
+      return 0;
+
+assert(0);
+#if 0
+    case DW_EH_PE_textrel:
+      return _Unwind_GetTextRelBase (context);
+    case DW_EH_PE_datarel:
+      return _Unwind_GetDataRelBase (context);
+    case DW_EH_PE_funcrel:
+      return _Unwind_GetRegionStart (context);
+#endif
+    }
+  __gxx_abort ();
+}
+
+#endif
+
+/* Read an unsigned leb128 value from P, store the value in VAL, return
+   P incremented past the value.  We assume that a word is large enough to
+   hold any value so encoded; if it is smaller than a pointer on some target,
+   pointers should not be leb128 encoded on that target.  */
+
+static unsigned char *
+read_uleb128 (unsigned char *p, _uleb128_t *val)
+{
+  unsigned int shift = 0;
+  unsigned char byte;
+  _uleb128_t result;
+
+  result = 0;
+  do
+    {
+      byte = *p++;
+      result |= ((_uleb128_t)byte & 0x7f) << shift;
+      shift += 7;
+    }
+  while (byte & 0x80);
+
+  *val = result;
+  return p;
+}
+
+/* Similar, but read a signed leb128 value.  */
+
+static unsigned char *
+read_sleb128 (unsigned char *p, _sleb128_t *val)
+{
+  unsigned int shift = 0;
+  unsigned char byte;
+  _uleb128_t result;
+
+  result = 0;
+  do
+    {
+      byte = *p++;
+      result |= ((_uleb128_t)byte & 0x7f) << shift;
+      shift += 7;
+    }
+  while (byte & 0x80);
+
+  /* Sign-extend a negative value.  */
+  if (shift < 8 * sizeof(result) && (byte & 0x40) != 0)
+    result |= -(((_uleb128_t)1L) << shift);
+
+  *val = (_sleb128_t) result;
+  return p;
+}
+
+typedef unsigned _Unwind_Internal_Ptr __attribute__((__mode__(__pointer__)));
+
+_Unwind_Internal_Ptr deref_unwind_ptr(uintptr_t to_deref);
+
+
+
+/* Load an encoded value from memory at P.  The value is returned in VAL;
+   The function returns P incremented past the value.  BASE is as given
+   by base_of_encoded_value for this encoding in the appropriate context.  */
+
+static unsigned char *
+read_encoded_value_with_base (unsigned char encoding, _Unwind_Ptr base,
+			      unsigned char *p, _Unwind_Ptr *val)
+{
+  union unaligned
+    {
+      void *ptr;
+      unsigned u2 __attribute__ ((mode (HI)));
+      unsigned u4 __attribute__ ((mode (SI)));
+      unsigned u8 __attribute__ ((mode (DI)));
+      signed s2 __attribute__ ((mode (HI)));
+      signed s4 __attribute__ ((mode (SI)));
+      signed s8 __attribute__ ((mode (DI)));
+    } __attribute__((__packed__));
+
+  union unaligned *u = (union unaligned *) p;
+  _Unwind_Internal_Ptr result;
+
+
+#define deref_unwind_ptr_in_memory(a) \
+		( ptrsize==4 ? (*(int32_t*)(a)) : (*(int64_t*)(a))  )
+
+  if (encoding == DW_EH_PE_aligned)
+    {
+      _Unwind_Internal_Ptr a = (_Unwind_Internal_Ptr) p;
+      a = (a + ptrsize - 1) & - ptrsize;
+      result = *(_Unwind_Internal_Ptr *) a;
+      result = deref_unwind_ptr_in_memory(a);
+      p = (unsigned char *) (_Unwind_Internal_Ptr) (a + ptrsize);
+    }
+  else
+    {
+      switch (encoding & 0x0f)
+	{
+	case DW_EH_PE_absptr:
+	  if(ptrsize==4)
+	  	result = (_Unwind_Internal_Ptr) u->u4;
+	  else if(ptrsize==8)
+	  	result = (_Unwind_Internal_Ptr) u->u8;
+	  else
+	 	assert(0);
+	  p += ptrsize;
+	  break;
+
+	case DW_EH_PE_uleb128:
+	  {
+	    _uleb128_t tmp;
+	    p = read_uleb128 (p, &tmp);
+	    result = (_Unwind_Internal_Ptr) tmp;
+	  }
+	  break;
+
+	case DW_EH_PE_sleb128:
+	  {
+	    _sleb128_t tmp;
+	    p = read_sleb128 (p, &tmp);
+	    result = (_Unwind_Internal_Ptr) tmp;
+	  }
+	  break;
+
+	case DW_EH_PE_udata2:
+	  result = u->u2;
+	  p += 2;
+	  break;
+	case DW_EH_PE_udata4:
+	  result = u->u4;
+	  p += 4;
+	  break;
+	case DW_EH_PE_udata8:
+	  result = u->u8;
+	  p += 8;
+	  break;
+
+	case DW_EH_PE_sdata2:
+	  result = u->s2;
+	  p += 2;
+	  break;
+	case DW_EH_PE_sdata4:
+	  result = u->s4;
+	  p += 4;
+	  break;
+	case DW_EH_PE_sdata8:
+	  result = u->s8;
+	  p += 8;
+	  break;
+
+	default:
+	  __gxx_abort ();
+	}
+
+      if (result != 0)
+	{
+	  result += ((encoding & 0x70) == DW_EH_PE_pcrel
+		     ? (_Unwind_Internal_Ptr) ptr_to_data_to_addr((uintptr_t)u) : base);
+//		     ? (_Unwind_Internal_Ptr) ((uintptr_t)u+(uintptr_t)eh_offset) : base);
+
+	  if (encoding & DW_EH_PE_indirect)
+	  {
+		result=deref_unwind_ptr(result);
+	    	//result = *(_Unwind_Internal_Ptr *) ((uintptr_t)result-(uintptr_t)eh_offset);
+	  }
+	}
+    }
+
+  *val = result;
+  return p;
+}
+
+#ifndef NO_BASE_OF_ENCODED_VALUE
+
+/* Like read_encoded_value_with_base, but get the base from the context
+   rather than providing it directly.  */
+
+static inline unsigned char *
+read_encoded_value (struct _Unwind_Context *context, unsigned char encoding,
+		    unsigned char *p, _Unwind_Ptr *val)
+{
+  return read_encoded_value_with_base (encoding,
+		base_of_encoded_value (encoding, context),
+		p, val);
+}
+
+#endif
+
+#endif /* unwind-pe.h */
diff --git a/irdb-lib/lib/.ignore b/irdb-lib/lib/.ignore
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/irdb-lib/libEXEIO/SConscript b/irdb-lib/libEXEIO/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..4b924974526de19e32967a8f64104b68348ed8b1
--- /dev/null
+++ b/irdb-lib/libEXEIO/SConscript
@@ -0,0 +1,9 @@
+import os
+
+Import('env')
+
+lib1=SConscript("src/SConscript")
+lib2=SConscript("test/SConscript")
+
+ret=[lib1, lib2]
+Return ('ret')
diff --git a/irdb-lib/libEXEIO/SConstruct b/irdb-lib/libEXEIO/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b5b7b78c5f88640c7e8877a9df76dc9191af7498
--- /dev/null
+++ b/irdb-lib/libEXEIO/SConstruct
@@ -0,0 +1,8 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return('lib')
diff --git a/irdb-lib/libEXEIO/include/exeio.h b/irdb-lib/libEXEIO/include/exeio.h
new file mode 100644
index 0000000000000000000000000000000000000000..f27c8556d7af114c2759766074643f751156ea5d
--- /dev/null
+++ b/irdb-lib/libEXEIO/include/exeio.h
@@ -0,0 +1,150 @@
+#ifndef EXEIO_H
+#define EXEIO_H
+
+#include <ostream>
+#include <vector>
+#include <stddef.h>
+#include <stdint.h>
+#include <assert.h>
+
+
+namespace EXEIO
+{
+	class exeio_t; // forward decl
+
+	typedef enum { ELF64, ELF32, PE32, PE64 } execlass_t;
+	typedef enum {  mtX86_64, mtI386, mtArm32, mtAarch64 } MachineType_t; 
+
+	typedef uintptr_t virtual_offset_t;
+
+
+	// create type to match elfio
+	class exeio_section_t
+	{
+		public: 
+			virtual ~exeio_section_t() {}  
+			virtual bool isLoadable() const =0;
+			virtual bool isExecutable() const =0;
+			virtual bool isWriteable() const =0;
+			virtual bool isReadable() const =0;
+			virtual bool isBSS() const =0;
+			virtual bool isThreadLocal() const { return false; }
+			virtual const char* get_data() const =0;
+			virtual std::string get_name() const =0;
+			virtual int get_size() const =0;
+			virtual int get_type() const =0;
+			virtual EXEIO::virtual_offset_t get_address() const =0;
+			virtual bool mightContainStrings() const =0;
+	};		
+
+	// break naming rule for elfio compatibility
+	typedef exeio_section_t section;
+		
+	class exeio_backend_t
+	{
+		public:
+			virtual ~exeio_backend_t() { }
+			virtual void dump_header(std::ostream& stream) =0;
+			virtual void dump_section_headers(std::ostream& stream) =0;
+			virtual void load(exeio_t* main, const char* filename) =0;
+                        virtual execlass_t get_class() =0;
+                        virtual MachineType_t getMachineType() const =0;
+			virtual virtual_offset_t get_entry() =0;
+			virtual void* get_elfio() { return NULL; }
+			virtual bool isDLL() =0;
+			virtual bool isDynamicallyLinked() { return true; }
+
+	};
+	
+	class exeio_sections_t
+	{
+		public:
+			exeio_section_t* operator[](int i) { return the_sections[i]; }
+			exeio_section_t* operator[](const std::string& name) 
+			{ 
+				for(auto s: the_sections)
+					if(s->get_name()==name)
+							return s;
+				return NULL;
+			}
+			exeio_section_t* findByAddress(const uint64_t addr)
+			{ 
+				for(auto s: the_sections)
+				{
+					if(s->get_address() <= addr &&  addr < (s->get_address()+s->get_size()))
+						return s;
+				}
+				return NULL;
+			}
+			int size() const { return (int)the_sections.size(); }
+
+			void add_section(exeio_section_t* sec)
+			{
+				the_sections.push_back(sec);
+			}
+		private:
+		
+			std::vector<exeio_section_t*> the_sections;
+
+		friend class exeio_backend_t;
+		
+	};
+
+
+	class exeio_t
+	{
+		public:
+			// constructors
+			exeio_t()  { Init(); }
+			exeio_t(const char* filename) { Init(); load(filename); }
+			exeio_t(const std::string& filename) { Init(); load(filename.c_str()); }
+			virtual ~exeio_t() { delete backend; }
+
+			virtual void load(const std::string filename) { load((char*)filename.c_str()); }
+
+			// load the file
+			virtual void load(const char* fn);
+
+			// trying to do minimal rewriting of code that uses
+			// ELFIO namespace.  
+			// This slightly odd construction of classes
+			// is used by ELFIO because it makes for nice looking code when using ELFIO.
+			// I quite like the results and there's a lot of code, so I'm mimicking it here.
+			// Unfortunately it means a less-than-clean interface for the class writer, 
+			// but we'll manage.
+			exeio_sections_t sections;
+
+			virtual virtual_offset_t get_entry() { assert(backend); return backend->get_entry(); }
+		
+			virtual void dump_header(std::ostream& stream) { assert(backend); backend->dump_header(stream); }
+			virtual void dump_section_headers(std::ostream& stream) { assert(backend); backend->dump_section_headers(stream); }
+                        virtual execlass_t get_class() { assert(backend); return backend->get_class(); }
+                        virtual MachineType_t getMachineType() const { assert(backend); return backend->getMachineType(); }
+			virtual void* get_elfio() { assert(backend); return backend->get_elfio(); }
+			virtual bool isDLL() { assert(backend); return backend->isDLL(); }
+			virtual bool isDynamicallyLinked() { assert(backend); return backend->isDynamicallyLinked(); }
+
+		private:
+			void Init() { backend=NULL; }
+
+			exeio_backend_t* backend;
+
+		friend class exeio_backend;
+			
+	};
+
+	// intentionally breaking _t rule for ELFIO compatibility.
+	typedef exeio_t exeio;
+
+	// breaking _t rule for ELFIO compatibility
+	class dump_t
+	{
+		public:
+		static void header(std::ostream& stream, EXEIO::exeio_t &to_print) { to_print.dump_header(stream); }
+		static void section_headers(std::ostream& stream, EXEIO::exeio_t &to_print) { to_print.dump_section_headers(stream); }
+	};
+	
+	typedef dump_t dump;
+
+}
+#endif
diff --git a/irdb-lib/libEXEIO/src/SConscript b/irdb-lib/libEXEIO/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..3a81a1b36c99bf204a68e16461c9c9633d0dc950
--- /dev/null
+++ b/irdb-lib/libEXEIO/src/SConscript
@@ -0,0 +1,29 @@
+import os
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+libname="EXEIO"
+files=  '''
+	exeio_src.cpp
+	'''
+
+cpppath=''' 
+	.
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libEXEIO/include
+	$SECURITY_TRANSFORMS_HOME/pebliss/trunk/pe_lib/
+	$SECURITY_TRANSFORMS_HOME/third_party/elfio-code
+	'''
+
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS=" -std=c++11 -Wall -Werror ")
+lib=myenv.SharedLibrary(libname, Split(files), LIBS=Split("irdb-core pebliss"), LIBPATH="$SECURITY_TRANSFORMS_HOME/lib" )
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libEXEIO/src/SConstruct b/irdb-lib/libEXEIO/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b5b7b78c5f88640c7e8877a9df76dc9191af7498
--- /dev/null
+++ b/irdb-lib/libEXEIO/src/SConstruct
@@ -0,0 +1,8 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return('lib')
diff --git a/irdb-lib/libEXEIO/src/exeio_elf.h b/irdb-lib/libEXEIO/src/exeio_elf.h
new file mode 100644
index 0000000000000000000000000000000000000000..cd2230b757b674a77aff6ab723d9ccdd1327a76d
--- /dev/null
+++ b/irdb-lib/libEXEIO/src/exeio_elf.h
@@ -0,0 +1,145 @@
+#ifndef EXEIO_ELF_H
+#define EXEIO_ELF_H
+
+#include <iostream>
+#include <vector>
+#include <assert.h>
+
+#pragma GCC diagnostic ignored "-Wsign-compare"
+#include "elfio/elfio.hpp"
+#include "elfio/elfio_dump.hpp"
+#include "elf.h"
+#pragma GCC diagnostic pop
+
+class exeio_backend;
+class exeio_section;
+
+namespace EXEIO
+{
+	class exeio_elf_section_t : public exeio_section_t
+	{
+		public:
+			exeio_elf_section_t(ELFIO::section *the_s) : s(the_s) { assert(s); }
+
+			bool isLoadable() const { return (s->get_flags() & SHF_ALLOC) == SHF_ALLOC; }
+			bool isExecutable() const { return (s->get_flags() & SHF_EXECINSTR) == SHF_EXECINSTR; }
+			bool isWriteable() const { return (s->get_flags() & SHF_WRITE) == SHF_WRITE; }
+                        bool isThreadLocal() const { return (s->get_flags() & SHF_TLS) == SHF_TLS; }
+			bool isReadable() const { return isLoadable(); }
+			bool isBSS() const { return (s->get_type() == SHT_NOBITS); }
+
+			const char* get_data() const { return s->get_data(); }
+			std::string get_name() const { return s->get_name(); }
+			int get_size() const { return s->get_size(); }
+			int get_type() const { return s->get_type(); }
+			EXEIO::virtual_offset_t get_address() const { return s->get_address(); }
+			bool mightContainStrings() const { assert(0); }
+
+		private:
+			ELFIO::section *s;
+	};
+
+	class exeio_elf_backend_t : public exeio_backend_t
+	{
+		public:
+			exeio_elf_backend_t() : e(NULL), main(NULL) {}
+			virtual ~exeio_elf_backend_t()
+			{
+				if(!main)
+					return;
+				// remove subclasses.
+				for(int i=0;i<e->sections.size(); ++i)
+				{
+					// copy each section into the main class' structure.
+					EXEIO::exeio_elf_section_t* sec=dynamic_cast<EXEIO::exeio_elf_section_t*>(main->sections[i]);
+					delete sec;
+				}
+
+				// remove the elfio class.
+				delete e;
+			}
+			void load(exeio* the_main, const char* filename)
+			{
+				main=the_main;
+				e=new ELFIO::elfio;	
+				int res=e->load(filename);
+				assert(res);
+
+				// resize the sections.
+				for(int i=0;i<e->sections.size(); ++i)
+				{
+					// copy each section into the main class' structure.
+					main->sections.add_section(new EXEIO::exeio_elf_section_t(e->sections[i]));
+				}
+	
+			}
+                        virtual void dump_header(std::ostream& stream) 
+			{
+				assert(e);
+				ELFIO::dump::header(stream,*e);
+			}
+                        virtual void dump_section_headers(std::ostream& stream) 
+			{
+				assert(e);
+				ELFIO::dump::section_headers(stream,*e);
+			}
+                        virtual execlass_t get_class() 
+			{
+				assert(e);
+				switch(e->get_class())  
+				{ 
+					case ELFCLASS64: return ELF64;
+					case ELFCLASS32: return ELF32;
+					default: assert(0);
+				};
+			}
+			virtual MachineType_t getMachineType() const
+			{
+				assert(e);
+				switch(e->get_machine())
+				{
+					case EM_ARM	: return mtArm32;
+					case EM_AARCH64	: return mtAarch64;
+					case EM_386     : return mtI386;
+					case EM_X86_64	: return mtX86_64;
+					default: assert(0);
+				}
+				assert(0);
+			}
+
+			// get entry point of function.
+                        virtual virtual_offset_t get_entry()
+			{
+				assert(e);
+				return (virtual_offset_t)e->get_entry();
+			}
+
+			virtual void* get_elfio() { return (void*)e; }
+
+                        virtual bool isDLL() { return e->get_type()!=ET_EXEC; }
+
+                        virtual bool isDynamicallyLinked() 
+			{ 
+				assert(e);
+				for(int i=0;i<e->segments.size(); ++i)
+				{
+					if( e->segments[i]->get_type()==PT_INTERP || e->segments[i]->get_type()==PT_DYNAMIC)
+						return true; 
+			
+				}
+				return false; 
+		
+			}
+
+
+
+	
+		private:  
+			ELFIO::elfio* e;
+			EXEIO::exeio* main;
+	};
+	
+
+}
+
+#endif
diff --git a/irdb-lib/libEXEIO/src/exeio_pe.h b/irdb-lib/libEXEIO/src/exeio_pe.h
new file mode 100644
index 0000000000000000000000000000000000000000..868ddeec9e26f2bd578b7e81b12130baa2394b3f
--- /dev/null
+++ b/irdb-lib/libEXEIO/src/exeio_pe.h
@@ -0,0 +1,169 @@
+#ifndef EXEIO_PE_H
+#define EXEIO_PE_H
+
+#ifndef SOLARIS
+#include <iostream>
+#include <vector>
+#include <assert.h>
+#include <fstream>
+
+#pragma GCC diagnostic ignored "-Wdeprecated-declarations"
+#include <pe_bliss.h>
+#pragma GCC diagnostic pop
+
+
+class exeio_backend;
+class exeio_section;
+
+
+namespace EXEIO
+{
+	class exeio_pe_section_t : public exeio_section_t
+	{
+		public:
+			exeio_pe_section_t(const pe_bliss::section *the_s, const pe_bliss::pe_base *the_b) 
+				: s(the_s),b(the_b) { assert(s); assert(b);}
+
+			bool isLoadable() const { return s->readable(); }
+			bool isExecutable() const { return s->executable(); }
+			bool isWriteable() const { return s->writeable(); }
+			bool isReadable() const { return s->readable(); }
+			bool isBSS() const  { return s->empty(); }
+			const char* get_data() const  { return s->get_raw_data().c_str(); }
+			std::string get_name() const { return s->get_name(); }
+			int get_size() const  { return s->get_virtual_size(); }
+			int get_type() const  { assert(0); } // not imp'd yet
+			EXEIO::virtual_offset_t get_address() const { 
+				EXEIO::virtual_offset_t base = b->get_image_base_64();
+				return base + s->get_virtual_address(); 
+			}
+			bool mightContainStrings() const { assert(0); }
+
+		private:
+			const pe_bliss::section *s;
+			const pe_bliss::pe_base *b;
+	};
+
+	class exeio_pe_backend_t : public exeio_backend_t
+	{
+		public:
+			exeio_pe_backend_t() 
+				: 
+				e(NULL), 
+				pe_sections(NULL),
+				main(NULL)
+			{
+			}
+
+			~exeio_pe_backend_t()
+			{
+				if(!main)
+					return;
+				// remove subclasses.
+				for(int i=0;i<main->sections.size(); ++i)
+				{
+					// copy each section into the main class' structure.
+					EXEIO::exeio_pe_section_t* sec=dynamic_cast<EXEIO::exeio_pe_section_t*>(main->sections[i]);			
+					delete sec;
+				}
+
+				// remove the pe_bliss class.
+				delete e;
+			}
+			void load(exeio* the_main, const char* filename)
+			{
+				main=the_main;
+
+				std::ifstream pe_file(filename, std::ios::in | std::ios::binary);
+        			if(!pe_file)
+        			{
+                			std::cerr << "Cannot open " << filename << std::endl;
+                			assert(0);
+					exit(1);
+        			}
+
+
+				e=new pe_bliss::pe_base(pe_bliss::pe_factory::create_pe(pe_file));
+				assert(e);
+
+				pe_sections=new pe_bliss::section_list(e->get_image_sections());
+
+                		for(pe_bliss::section_list::const_iterator it = pe_sections->begin(); 
+					it != pe_sections->end(); ++it)
+                		{
+                        		const pe_bliss::section& s = *it; 
+					main->sections.add_section(new EXEIO::exeio_pe_section_t(&s,e));
+				}
+
+	
+			}
+                        virtual void dump_header(std::ostream& stream) 
+			{
+				assert(e);
+
+                		std::cout << "EP : " <<std::hex<< e->get_ep() << std::endl;
+                		std::cout << "EP section name: " << e->section_from_rva(e->get_ep()).get_name() << std::endl;
+                		std::cout << "EP section data length: " << 
+					e->section_data_length_from_rva(e->get_ep()) << std::endl;
+
+                		if(e->has_imports())
+				{
+                        		std::cout << "Import section name: " << 
+						e->section_from_directory(pe_bliss::pe_win
+						::image_directory_entry_import).get_name() 
+						<< std::endl;
+				}
+			}
+                        virtual void dump_section_headers(std::ostream& stream) 
+			{
+				assert(e);
+                		for(pe_bliss::section_list::const_iterator it = pe_sections->begin(); 
+					it != pe_sections->end(); ++it)
+                		{
+                        		const pe_bliss::section& s = *it; //Секция
+                        		std::cout << "Section [" << s.get_name() << "]" << std::endl //Имя секции
+                                		<< "Characteristics: " << s.get_characteristics() << std::endl 
+                                		<< "Size of raw data: " << s.get_size_of_raw_data() << std::endl 
+                                		<< "Virtual address: " << s.get_virtual_address() << std::endl 
+                                		<< "Virtual size: " << s.get_virtual_size() << std::endl 
+                                		<< std::endl;
+                		}
+
+			}
+			virtual MachineType_t getMachineType() const
+			{
+				assert(0);
+			}
+
+                        virtual execlass_t get_class() 
+			{
+				assert(e);
+        			if(e->get_pe_type() == pe_bliss::pe_type_32)
+					return PE32;
+        			if(e->get_pe_type() == pe_bliss::pe_type_64)
+					return PE64;
+				assert(0);
+			}
+
+			// get entry point of function.
+                        virtual virtual_offset_t get_entry()
+			{
+				assert(e);
+				return (virtual_offset_t)e->get_ep();
+			}
+
+
+                        virtual bool isDLL() { assert(0); }
+
+
+	
+		private:  
+			pe_bliss::pe_base* e;
+			pe_bliss::section_list* pe_sections;
+			EXEIO::exeio* main;
+	};
+	
+
+}
+#endif // solaris
+#endif // exeio_pe_h
diff --git a/irdb-lib/libEXEIO/src/exeio_src.cpp b/irdb-lib/libEXEIO/src/exeio_src.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..58ec9f58b794f6402db38942f3d6c0bc6cde3ac2
--- /dev/null
+++ b/irdb-lib/libEXEIO/src/exeio_src.cpp
@@ -0,0 +1,51 @@
+
+
+#include <istream>
+#include <fstream>
+#include <exeio.h>
+#include <exeio_elf.h>
+#include <exeio_pe.h>
+
+
+
+using namespace EXEIO;
+using namespace std;
+#ifndef SOLARIS
+using namespace pe_bliss;
+#endif
+
+void exeio::load(const char* filename)
+{
+
+	ifstream instream(filename); 
+
+	if(!instream)
+		assert(0 && "Cannot open file");
+
+	int c0=instream.get();
+	int c1=instream.get();
+	int c2=instream.get();
+	int c3=instream.get();
+
+	// check for elf magic number
+	if(c0 == '\177' && c1=='E' && c2=='L' && c3=='F')
+	{
+		backend=new exeio_elf_backend_t;
+	}
+	// check for CGC magic number
+	else if(c0 == '\177' && c1=='C' && c2=='G' && c3=='C')
+	{
+		backend=new exeio_elf_backend_t;
+	}
+	else
+#ifndef SOLARIS
+		// we assume it's PE.
+		backend=new exeio_pe_backend_t;
+#else
+		// don't build win support on solaris.
+		assert(0);
+#endif
+
+	backend->load(this, filename);
+
+}
diff --git a/irdb-lib/libEXEIO/test/SConscript b/irdb-lib/libEXEIO/test/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..3982cf59c158574c0fe45309c02730d326d285b5
--- /dev/null
+++ b/irdb-lib/libEXEIO/test/SConscript
@@ -0,0 +1,38 @@
+import os
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+(sysname, nodename, release, version, machine)=os.uname()
+
+
+libname="exeio_test"
+files=  '''
+	main.cpp
+	'''
+
+cpppath=''' 
+	.
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libEXEIO/include
+	$SECURITY_TRANSFORMS_HOME/libEXEIO/include
+	'''
+libpath=''' 
+	$SECURITY_TRANSFORMS_HOME/lib/
+	'''
+
+libs=   '''
+	EXEIO
+	pebliss
+	'''
+if "CYGWIN" in sysname:
+	libs = libs + " iconv"
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath), LIBS=Split(libs), LIBPATH=Split(libpath))
+myenv.Append(CXXFLAGS=" -Wall -Werror -std=c++11 ")
+pgm=myenv.Program(libname, Split(files))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/bin/", pgm)
+Default(install)
+Return('install')
diff --git a/irdb-lib/libEXEIO/test/SConstruct b/irdb-lib/libEXEIO/test/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b3bd01322f2b78089fd86e0e9b0ae01897c9c8a5
--- /dev/null
+++ b/irdb-lib/libEXEIO/test/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+Return('lib')
diff --git a/irdb-lib/libEXEIO/test/main.cpp b/irdb-lib/libEXEIO/test/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..041d395f36ece81ab882115d7f097c0b19b200e7
--- /dev/null
+++ b/irdb-lib/libEXEIO/test/main.cpp
@@ -0,0 +1,23 @@
+#include <iostream>
+#include <exeio.h>
+
+using namespace std;
+using namespace EXEIO;
+
+
+int main(int argc, char* argv[])
+{
+	if(argc!=2)
+	{
+		cout<<"Usage: "<<argv[0]<<": <exe>"<<endl;
+	}
+
+	exeio *exep=new exeio;
+
+	exep->load(argv[1]);
+
+	EXEIO::dump::header(cout,*exep);
+	EXEIO::dump::section_headers(cout,*exep);
+
+	return 0;
+}
diff --git a/irdb-lib/libIRDB-cfg/include/BasicBlock.hpp b/irdb-lib/libIRDB-cfg/include/BasicBlock.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..d2059b22eca8bf27a7df1c8991de15116ede1822
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/include/BasicBlock.hpp
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+namespace libIRDB
+{
+	using namespace std;
+
+	class BasicBlock_t : public IRDB_SDK::BasicBlock_t
+	{
+
+		public:
+			BasicBlock_t();
+			virtual ~BasicBlock_t() { }
+
+			bool getIsExitBlock() const { return is_exit_block; }
+			void setIsExitBlock(bool is_exit) { is_exit_block=is_exit; }
+
+			IRDB_SDK::InstructionVector_t& GetInstructions() { return instructions; }
+			IRDB_SDK::BasicBlockSet_t&     GetPredecessors() { return predecessors; }
+			IRDB_SDK::BasicBlockSet_t&     GetSuccessors()   { return successors; }
+			IRDB_SDK::BasicBlockSet_t&     GetIndirectTargets() { return indirect_targets; }
+
+			// for const correctness if you aren't modifying.
+			const IRDB_SDK::InstructionVector_t& getInstructions()    const { return instructions; }
+			const IRDB_SDK::BasicBlockSet_t&     getPredecessors()    const { return predecessors; }
+			const IRDB_SDK::BasicBlockSet_t&     getSuccessors()      const { return successors; }
+			const IRDB_SDK::BasicBlockSet_t&     getIndirectTargets() const { return indirect_targets; }
+//			      IRDB_SDK::BasicBlock_t   *     getFallthrough()     const ;
+//			      IRDB_SDK::BasicBlock_t   *     getTarget()          const ;
+
+			bool endsInBranch() const;
+			bool endsInIndirectBranch() const;
+			bool endsInConditionalBranch() const;
+			IRDB_SDK::Instruction_t* getBranchInstruction() const;
+			void dump(ostream &os=cout) const ; 
+
+		protected:
+
+			void BuildBlock( IRDB_SDK::Instruction_t* insn,
+					const map<IRDB_SDK::Instruction_t*,BasicBlock_t*> &insn2block_map
+					);
+
+
+		private:
+
+			IRDB_SDK::InstructionVector_t instructions;
+			IRDB_SDK::BasicBlockSet_t  predecessors;
+			IRDB_SDK::BasicBlockSet_t  successors;
+			IRDB_SDK::BasicBlockSet_t  indirect_targets;
+			bool is_exit_block;
+
+		friend ostream& operator<<(ostream& os, const BasicBlock_t& block);
+		friend class ControlFlowGraph_t;
+	};
+
+
+}
diff --git a/irdb-lib/libIRDB-cfg/include/CFG.hpp b/irdb-lib/libIRDB-cfg/include/CFG.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..2499b994eea66f87fe85f49cd85dffaaa056489e
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/include/CFG.hpp
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+	using namespace std;
+
+	class ControlFlowGraph_t : public IRDB_SDK::ControlFlowGraph_t
+	{
+		public:
+			ControlFlowGraph_t(IRDB_SDK::Function_t* func);
+			virtual ~ControlFlowGraph_t() { }
+			IRDB_SDK::BasicBlock_t* getEntry() const { return entry; }
+			IRDB_SDK::Function_t* getFunction() const { return function; }
+			IRDB_SDK::BasicBlockSet_t& GetBlocks()   { return blocks; }
+			const IRDB_SDK::BasicBlockSet_t& getBlocks()   const { return blocks; }
+			void dump(ostream &os=cout) const; 
+			bool hasEdge(IRDB_SDK::BasicBlock_t *p_src, IRDB_SDK::BasicBlock_t *p_tgt) const;
+			IRDB_SDK::CFGEdgeType_t getEdgeType(const IRDB_SDK::BasicBlock_t *p_src, const IRDB_SDK::BasicBlock_t *p_tgt) const;
+
+		private:
+		// methods 
+			void Build(IRDB_SDK::Function_t *func);
+			void alloc_blocks(const IRDB_SDK::InstructionSet_t &starts, map<IRDB_SDK::Instruction_t*,BasicBlock_t*>& insn2block_map);
+			void build_blocks(const map<IRDB_SDK::Instruction_t*,BasicBlock_t*>& insn2block_map);
+			void find_unblocked_instructions(InstructionSet_t &starts, IRDB_SDK::Function_t* func);
+
+		// data
+			IRDB_SDK::BasicBlockSet_t blocks;
+			IRDB_SDK::BasicBlock_t* entry;
+			IRDB_SDK::Function_t* function;
+
+	};
+
+}
diff --git a/irdb-lib/libIRDB-cfg/include/callgraph.hpp b/irdb-lib/libIRDB-cfg/include/callgraph.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..bc5f383923e2e686c9c08325aa175a7b008db8b4
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/include/callgraph.hpp
@@ -0,0 +1,189 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef irdb_cfg_callgraph_h
+#define irdb_cfg_callgraph_h
+
+namespace libIRDB
+{
+
+	using namespace std;
+
+	// only one type of hell node for now, but leave
+	// open the possibilty for multiple hell nodes
+	typedef enum { DEFAULT_HELL_NODE = 0 } HellNodeType; 
+
+	class CallGraphNode_t : public IRDB_SDK::CallGraphNode_t
+	{
+		public:
+			virtual ~CallGraphNode_t(){ }
+			CallGraphNode_t(IRDB_SDK::Function_t* f = NULL) {
+				if (f) {
+					SetFunction(f);
+				} else {
+					m_isHellNode = true;
+					m_node.hellNodeType = DEFAULT_HELL_NODE;
+				}
+			}
+
+			bool isHellnode() const { return m_isHellNode; }
+
+			IRDB_SDK::Function_t* getFunction() const {
+				assert(!m_isHellNode);
+				if (m_isHellNode) 
+					return NULL;					
+				else
+					return m_node.func;
+			}
+
+			HellNodeType GetHellNodeType() const {
+				assert(m_isHellNode);
+				return m_node.hellNodeType;
+			}
+
+			bool operator==(const CallGraphNode_t &other) const {
+				if (this == &other) return true;
+				if (m_isHellNode)
+				{
+					return m_node.hellNodeType == other.m_node.hellNodeType;
+				}
+				else
+					return m_node.func == other.m_node.func;
+			}
+			void dump(ostream& os=cout) const;
+
+		private:
+			void SetFunction(IRDB_SDK::Function_t* const f) {
+				assert(f);
+				m_node.func = f;
+				m_isHellNode = false;
+			}
+
+		private:
+			bool m_isHellNode;
+			union {
+				IRDB_SDK::Function_t* func;
+				HellNodeType hellNodeType;
+			} m_node;
+	};
+
+
+	class Callgraph_t : public IRDB_SDK::CallGraph_t
+	{
+		public:
+			Callgraph_t();
+			virtual ~Callgraph_t();
+			void addFile(IRDB_SDK::FileIR_t* const firp);
+
+			bool edgeExists(const IRDB_SDK::CallGraphEdge_t& edge) const
+			{
+				const auto from = dynamic_cast<CallGraphNode_t*>(edge.first);
+				const auto to   = dynamic_cast<CallGraphNode_t*>(edge.second);
+					
+				const auto caller_it  = callers.find(from);
+				if(caller_it==callers.end())
+					return false;
+
+				const auto &calleeSet = caller_it->second;
+				return calleeSet.find(to)!=calleeSet.end();
+			}
+			bool edgeExists(IRDB_SDK::CallGraphNode_t& n1, IRDB_SDK::CallGraphNode_t& n2)  const
+				{ return edgeExists(IRDB_SDK::CallGraphEdge_t(&n1,&n2));}
+
+			IRDB_SDK::CallGraphNodeSet_t& GetCallersOfNode(IRDB_SDK::CallGraphNode_t* const node)
+				{ return callers[node]; }
+			IRDB_SDK::CallGraphNodeSet_t& GetCalleesOfNode(IRDB_SDK::CallGraphNode_t* const node)
+				{ return callees[node]; }
+
+			const IRDB_SDK::CallGraphNodeSet_t& getCallersOfNode(IRDB_SDK::CallGraphNode_t* const node) const
+			{ 
+				static const auto empty = IRDB_SDK::CallGraphNodeSet_t();
+				const auto it=callers.find(node);
+				return (it==callers.end()) ?  empty : it->second;
+			}
+			const IRDB_SDK::CallGraphNodeSet_t& getCalleesOfNode(IRDB_SDK::CallGraphNode_t* const node) const
+			{ 
+				static const auto empty = IRDB_SDK::CallGraphNodeSet_t();
+				const auto it=callees.find(node);
+				return (it==callees.end()) ?  empty : it->second;
+			}
+			
+			void GetAncestors(IRDB_SDK::Function_t* const fn, IRDB_SDK::CallGraphNodeSet_t& ancestors, bool skipHellNode = false) const;
+			void GetAncestors(IRDB_SDK::CallGraphNode_t* const node, IRDB_SDK::CallGraphNodeSet_t& ancestors, bool skipHellNode = false) const;
+
+			const IRDB_SDK::CallSiteSet_t& GetCallSites(IRDB_SDK::CallGraphNode_t* const n1) const
+			{ 
+				static const auto empty = IRDB_SDK::CallSiteSet_t();
+				const auto it=call_sites.find(n1);
+				return (it==call_sites.end()) ?  empty : it->second;
+			}
+			
+
+			IRDB_SDK::CallSiteSet_t& getCallSites(IRDB_SDK::CallGraphNode_t* const n1)
+				{ return call_sites[n1]; }
+
+			void dump(ostream& fout) const;
+
+			string GetNodeName(const IRDB_SDK::CallGraphNode_t* const p_n1) const {
+				auto n1=dynamic_cast<CallGraphNode_t const*>(p_n1);
+				assert(n1);
+				if (n1->isHellnode()) {
+					ostringstream s;
+					s << "HELLNODE" << n1->GetHellNodeType();
+					return s.str();
+				} else {
+					assert(n1->getFunction());
+					return n1->getFunction()->getName(); 
+				}
+			}
+
+			string GetCallsiteDisassembly(const IRDB_SDK::CallSite_t &c) const
+				{ return c ? c->getDisassembly() : "NOFROMFUNC"; } 
+
+			bool isReachable(IRDB_SDK::CallGraphNode_t* const from, IRDB_SDK::CallGraphNode_t* const to, bool skipHellNode = false) const;
+
+			CallGraphNode_t& GetDefaultHellNode() { return default_hellnode; }
+			const CallGraphNode_t& getDefaultHellNode() const { return default_hellnode; }
+
+			IRDB_SDK::CallGraphNode_t* findNode(IRDB_SDK::Function_t* const fn) const;
+
+		private:
+			// create nodes from functions
+			void CreateNodes(IRDB_SDK::FileIR_t *firp);
+
+			// mark the given insn as a call site.
+			void MarkCallSite(IRDB_SDK::Instruction_t* const insn);
+
+			// traverse graph to retrieve all ancestors
+			void _GetAncestors(IRDB_SDK::CallGraphNode_t* const node, IRDB_SDK::CallGraphNodeSet_t &ancestors, IRDB_SDK::CallGraphNodeSet_t &visited, bool skipHellNode) const;
+
+			using CGNodeToCGNodeSetMap_t = map<IRDB_SDK::CallGraphNode_t*, IRDB_SDK::CallGraphNodeSet_t > ;
+			using NodeToCallSiteSetMap_t = map<IRDB_SDK::CallGraphNode_t*, IRDB_SDK::CallSiteSet_t      > ;
+			using FunctionToCGNodeMap_t  = map<IRDB_SDK::Function_t*     , IRDB_SDK::CallGraphNode_t*   > ;
+;
+			CGNodeToCGNodeSetMap_t callers;     // map a callee to its callees
+			CGNodeToCGNodeSetMap_t callees;     // map a caller to its callers
+			NodeToCallSiteSetMap_t call_sites;
+			CallGraphNode_t default_hellnode;   // default hell node
+			FunctionToCGNodeMap_t nodes;        // maps functions to call graph nodes
+	};
+
+}
+#endif
diff --git a/irdb-lib/libIRDB-cfg/include/criticaledge.hpp b/irdb-lib/libIRDB-cfg/include/criticaledge.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..244e68347ab77f4e565bb300fc98e8a6b4e81911
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/include/criticaledge.hpp
@@ -0,0 +1,39 @@
+/*
+ * Copyright (c) 2019 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+	using namespace std;
+
+	class CriticalEdgeAnalyzer_t : public IRDB_SDK::CriticalEdges_t
+	{
+		public:
+			CriticalEdgeAnalyzer_t(const ControlFlowGraph_t *p_cfg, const bool p_conservative=true);
+			virtual ~CriticalEdgeAnalyzer_t() { }
+			const IRDB_SDK::BasicBlockEdgeSet_t& getAllCriticalEdges() const { return criticals; }
+
+		private:
+			void init();
+			const IRDB_SDK::ControlFlowGraph_t *m_cfg;
+			const bool m_conservative;
+		        IRDB_SDK::BasicBlockEdgeSet_t criticals;
+
+	};
+}
diff --git a/irdb-lib/libIRDB-cfg/include/domgraph.hpp b/irdb-lib/libIRDB-cfg/include/domgraph.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..db37459ae80730a03cc2a15e599ba5b8003d5a72
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/include/domgraph.hpp
@@ -0,0 +1,75 @@
+#include <ostream>
+namespace libIRDB
+{
+	using namespace std;
+
+        using  DominatorMap_t    = map<IRDB_SDK::BasicBlock_t*, IRDB_SDK::BasicBlockSet_t>;
+        using  BlockToBlockMap_t = map<IRDB_SDK::BasicBlock_t*, IRDB_SDK::BasicBlock_t*>;
+
+
+
+
+
+	class DominatorGraph_t : public IRDB_SDK::DominatorGraph_t
+	{
+		public:
+			DominatorGraph_t(const ControlFlowGraph_t* p_cfg, bool needs_postdoms=false, bool needs_idoms=false);
+			virtual ~DominatorGraph_t() { } 
+
+
+			// get the (post) dominators for a node 
+			IRDB_SDK::BasicBlockSet_t& GetDominators(IRDB_SDK::BasicBlock_t* node) { return dom_graph[node]; }
+			IRDB_SDK::BasicBlockSet_t& GetPostDominators(IRDB_SDK::BasicBlock_t* node) { return post_dom_graph[node]; }
+
+			const IRDB_SDK::BasicBlockSet_t& getDominators(const IRDB_SDK::BasicBlock_t* node) const { return dom_graph.at(const_cast<IRDB_SDK::BasicBlock_t*>(node)); }
+			const IRDB_SDK::BasicBlockSet_t& getDominated (const IRDB_SDK::BasicBlock_t* node) const { return dominated_graph.at(const_cast<IRDB_SDK::BasicBlock_t*>(node)); }
+// 			const IRDB_SDK::BasicBlockSet_t& getPostDominators(const IRDB_SDK::BasicBlock_t* node) const { assert(0); } 
+// 			const IRDB_SDK::BasicBlockSet_t& getPostDominated (const IRDB_SDK::BasicBlock_t* node) const { assert(0); } 
+
+			bool hasWarnings() const { return warn; }
+
+
+			// get the immeidate (post) dominators for a node 
+			const IRDB_SDK::BasicBlock_t*    getImmediateDominator    (const IRDB_SDK::BasicBlock_t* node)  const 
+			{ 
+				auto it=idom_graph.find(const_cast<IRDB_SDK::BasicBlock_t*>(node)); 
+				return (it!=idom_graph.end()) ? it->second : nullptr; 
+			}
+			const IRDB_SDK::BasicBlockSet_t& getImmediateDominated    (const IRDB_SDK::BasicBlock_t* node)  const 
+			{ 
+				const static IRDB_SDK::BasicBlockSet_t empty;
+				auto it=idominated_graph.find(const_cast<IRDB_SDK::BasicBlock_t*>(node)); 
+				return (it!=idominated_graph.end()) ? it->second : empty; }
+// 			const IRDB_SDK::BasicBlock_t*    getImmediatePostDominator(const IRDB_SDK::BasicBlock_t* node)  const { assert(0); } 
+// 			const IRDB_SDK::BasicBlockSet_t& getImmediatePostDominated(const IRDB_SDK::BasicBlock_t* node)  const { assert(0); } 
+
+			void dump(ostream& os=cout) const; 
+
+
+		private:
+			void Dominated_Compute();
+
+			using pred_func_ptr_t =  const IRDB_SDK::BasicBlockSet_t& (*) (const IRDB_SDK::BasicBlock_t* node);
+
+			DominatorMap_t Dom_Comp(const IRDB_SDK::BasicBlockSet_t& N, pred_func_ptr_t pred_func, IRDB_SDK::BasicBlock_t* r);
+			BlockToBlockMap_t Idom_Comp(const IRDB_SDK::BasicBlockSet_t& N, const DominatorMap_t &Domin, IRDB_SDK::BasicBlock_t* r);
+
+
+			DominatorMap_t dom_graph;
+			BlockToBlockMap_t idom_graph;
+
+			DominatorMap_t dominated_graph;
+			DominatorMap_t idominated_graph;
+
+			DominatorMap_t post_dom_graph;
+			BlockToBlockMap_t post_idom_graph;
+
+			const ControlFlowGraph_t& cfg;	// a reference to our cfg.
+
+			bool warn;
+
+	};
+
+
+
+}
diff --git a/irdb-lib/libIRDB-cfg/include/libIRDB-cfg.hpp b/irdb-lib/libIRDB-cfg/include/libIRDB-cfg.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..003113796c76bed60fd626b097b7ad11b00bef7d
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/include/libIRDB-cfg.hpp
@@ -0,0 +1,41 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef libIRDB_cfg
+#define libIRDB_cfg
+
+
+/* Building a CFG depends on core functionality */
+#include <irdb-cfg>
+#include <libIRDB-core.hpp>
+
+#include <vector>
+#include <set>
+#include <map>
+#include <ostream>
+
+#include <BasicBlock.hpp>
+#include <CFG.hpp>
+#include <callgraph.hpp>
+#include <domgraph.hpp>
+#include <criticaledge.hpp>
+
+
+#endif
diff --git a/irdb-lib/libIRDB-cfg/src/BasicBlock.cpp b/irdb-lib/libIRDB-cfg/src/BasicBlock.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e89e6664e805291a2ffc4674957353cdae319fb9
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/BasicBlock.cpp
@@ -0,0 +1,259 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <map>
+#include <libIRDB-core.hpp>
+#include <libIRDB-cfg.hpp>
+#include <irdb-util>
+#include <algorithm>
+
+using namespace libIRDB;
+using namespace std;
+
+
+#define ALLOF(a) begin((a)), end((a))
+
+/*
+ * is_in_container - a handle template function returning whether key S is contained in container T.
+ */
+template <class T, class S>
+inline bool is_in_container(const T& container, const S& key)
+{
+	bool is_in=container.find(key) != container.end();
+	return is_in;
+}
+
+template <class S>
+inline bool is_in_set(const std::set<S>& container, const S& key)
+{
+	return std::find(container.begin(), container.end(), key) != container.end();
+}
+/*
+ * find_map_object - without modifying the object, return the element
+ */
+template <class T, class S>
+inline S const& find_map_object( const std::map< T , S > &a_map, const T& key)
+{
+	const auto it=a_map.find(key);
+	assert(it!=a_map.end());
+
+	return (*it).second;
+}
+
+
+
+BasicBlock_t::BasicBlock_t() 
+	: is_exit_block(false)
+{
+}
+
+
+
+void BasicBlock_t::BuildBlock
+	(
+		IRDB_SDK::Instruction_t* insn, 
+		const map<IRDB_SDK::Instruction_t*,BasicBlock_t*> &insn2block_map
+	)
+{
+	const auto &func=insn->getFunction();
+	assert(insn);
+	/* loop through the instructions for this block */
+	while(insn)
+	{
+		const auto d = DecodedInstruction_t::factory(insn);
+
+		/* insert this instruction */
+		instructions.push_back(insn);
+
+		auto target_insn=insn->getTarget();
+		auto ft_insn=insn->getFallthrough();
+
+		/* determine if there's a target block */
+		BasicBlock_t* target_block=nullptr;
+		const auto include_target = (!d->isCall());
+		if (include_target && target_insn && is_in_container(insn2block_map,target_insn)) 
+			target_block=find_map_object(insn2block_map,target_insn);
+
+		/* determine if there's a ft block */
+		BasicBlock_t* ft_block=nullptr;
+		if(ft_insn && is_in_container(insn2block_map,ft_insn))
+			ft_block=find_map_object(insn2block_map,ft_insn);
+
+		/* if there's a target block, insert it into the appropriate sets */
+		if(target_block)
+		{
+			target_block->GetPredecessors().insert(this);
+			successors.insert(target_block);
+		}
+
+		/* This is also the end of the block if this is a function exit instruction */
+		if(insn->isFunctionExit()) 
+		{
+			is_exit_block=true;
+		}
+
+		// handle fixed-call fallthroughs.
+		// for_each(ALLOF(insn->getRelocations()),  [this,&insn2block_map](IRDB_SDK::Relocation_t* reloc)
+		for(auto reloc : insn->getRelocations())
+		{
+			// and has a reloc that's a pcrel with a WRT object 
+			// possible for a call to have a null fallthrouth (and consequently null WRT)
+			// becauase the call may be the last insn in a section, etc.
+			if( reloc->getType()==string("fix_call_fallthrough") && reloc->getWRT()!=nullptr) 
+			{
+				assert(reloc->getWRT()!=nullptr);
+				auto fix_call_fallthrough_insn=dynamic_cast<Instruction_t*>(reloc->getWRT());
+				assert(fix_call_fallthrough_insn);
+
+				// this block has a fallthrough to the return block.
+				if(is_in_container(insn2block_map,fix_call_fallthrough_insn))
+				{
+					BasicBlock_t* fix_call_fallthrough_blk=find_map_object(insn2block_map,static_cast<IRDB_SDK::Instruction_t*>(fix_call_fallthrough_insn));
+					successors.insert(fix_call_fallthrough_blk);
+					fix_call_fallthrough_blk->GetPredecessors().insert(this);
+				}
+
+				is_exit_block=false;
+			}
+		};
+
+
+		/* if there's a fallthrough block, insert it into the appropriate sets */
+		if(ft_block)
+		{
+			ft_block->GetPredecessors().insert(this);
+			successors.insert(ft_block);
+		}
+			
+		/* this is the end of the block if there's a target instruction */
+		if(target_insn)
+			break;
+
+		/* or if there is a fallthrough block already built */
+		if(ft_block)
+			break;
+
+		/* check for a fallthrough out of the function */
+		if(ft_insn && ft_insn->getFunction() != func) 
+			break;
+
+
+		/* otherwise, move to the fallthrough */
+		insn=ft_insn;
+	}
+
+
+	// deal with IB targets for the end of the block
+
+	insn=instructions[instructions.size()-1]; // get last instruction.
+	assert(insn);
+	const auto icfs         = insn->getIBTargets();
+	const auto d            = DecodedInstruction_t::factory(insn);
+	const auto include_icfs = !(d->isReturn() || d->isCall() ) ;
+
+
+	if(icfs != nullptr && include_icfs)
+	{
+		for(const auto target : *icfs)
+		{
+			if(is_in_container(insn2block_map,target) && target!=func->getEntryPoint())	// don't link calls to the entry block.
+			{
+				BasicBlock_t* target_block=find_map_object(insn2block_map,target);
+				target_block->GetPredecessors().insert(this);
+				successors.insert(target_block);
+			}
+		};
+	}
+	
+}
+
+
+
+bool BasicBlock_t::endsInBranch()  const
+{
+	const auto branch=instructions[instructions.size()-1];	
+	assert(branch);
+
+	const auto d=DecodedInstruction_t::factory(branch);
+	return d->isBranch();
+
+	
+}
+bool BasicBlock_t::endsInIndirectBranch()  const
+{
+	const auto *branch=instructions[instructions.size()-1];	
+	assert(branch);
+
+	const auto p_d=DecodedInstruction_t::factory(branch);
+	const auto &d =*p_d;
+
+	if(d.isReturn())
+		return true;
+	if(d.isUnconditionalBranch() || d.isCall())
+	{
+		if(!d.getOperand(0)->isConstant())
+			/* not a constant type */
+			return true;
+		return false;
+		
+	}
+	return false;
+}
+bool BasicBlock_t::endsInConditionalBranch() const
+{
+	if(!endsInBranch())
+		return false;
+	const auto branch=instructions[instructions.size()-1];	
+	assert(branch);
+	const auto d=DecodedInstruction_t::factory(branch);
+
+	return d->isConditionalBranch(); 
+}
+
+IRDB_SDK::Instruction_t* BasicBlock_t::getBranchInstruction() const
+
+{
+	if(!endsInBranch())
+		return nullptr;
+
+	auto branch=instructions[instructions.size()-1];	
+	return branch;
+}
+
+
+std::ostream& IRDB_SDK::operator<<(std::ostream& os, const IRDB_SDK::BasicBlock_t& block)
+{
+	block.dump(os);
+	return os;
+}
+void  BasicBlock_t::dump(std::ostream& os) const
+{
+	os<<getIsExitBlock();
+	os<<"\t ---- Starting block print -----" <<endl;
+	for(auto i=0U;i<getInstructions().size();i++)
+	{
+		const auto insn=getInstructions()[i];
+		os<<"\t Instruction "<<std::dec<<i<<" at " << std::hex << insn->getAddress()->getVirtualOffset() << " with id " << std::dec << insn->getBaseID() << " " << insn->getComment() << endl;
+	}
+	os<<"\t ---- done block print -----" <<endl;
+	os<<endl;
+}
+
diff --git a/irdb-lib/libIRDB-cfg/src/CFG.cpp b/irdb-lib/libIRDB-cfg/src/CFG.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..33b9b56ac5b1c5fb96214aa910ecd53fa6bbef93
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/CFG.cpp
@@ -0,0 +1,277 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <libIRDB-cfg.hpp>
+#include <irdb-util>
+#include <algorithm>
+
+using namespace std;
+using namespace libIRDB;
+
+#define ALLOF(a) begin((a)), end((a))
+
+/*
+ * is_in_container - a handle template function returning whether key S is contained in container T.
+ */
+template <class T, class S>
+inline bool is_in_container(const T& container, const S& key)
+{
+        bool is_in=container.find(key) != container.end();
+        return is_in;
+}
+
+template <class S>
+inline bool is_in_set(const std::set<S>& container, const S& key)
+{
+        return std::find(container.begin(), container.end(), key) != container.end();
+}
+/*
+ * find_map_object - without modifying the object, return the element
+ */
+template <class T, class S>
+inline S const& find_map_object( const std::map< T , S > &a_map, const T& key)
+{
+        const auto it=a_map.find(key);
+        assert(it!=a_map.end());
+
+        return (*it).second;
+}
+
+
+/*
+ *  FindTargets - locate all possible instructions that are the target of a jump instruction
+ */
+static InstructionSet_t FindBlockStarts(IRDB_SDK::Function_t* func) 
+{
+
+	InstructionSet_t targets;
+	InstructionSet_t found_fallthrough_to;
+
+	if(func->getEntryPoint())
+		/* the entry point of the function is a target instruction for this CFG */
+		targets.insert(func->getEntryPoint());
+
+	/* for each instruction, decide if it's a block start based on whether or not 
+	 * it can be indirectly branched to.  Also mark direct targets as block starts.
+	 */
+	for(auto insn : func->getInstructions())
+	{
+		/* If this instruction might be an indirect branch target, then mark it as a block start */
+		if(insn->getIndirectBranchTargetAddress())
+		{
+			targets.insert(insn);
+		}
+
+		/* get target and fallthrough */
+		auto target=insn->getTarget();
+		auto ft=insn->getFallthrough();
+
+		/* if this instruction has a target, and the target is in this function, mark the target as a block start */
+		if(target && is_in_container(func->getInstructions(), target))
+			targets.insert(target);
+
+		/* there is a target, and a failthrough, and the fallthrough is in this function */
+		if(target && ft && is_in_container(func->getInstructions(), ft))
+			targets.insert(ft);
+
+		// we already found a fallthrough to ft, so we have 2+ fallthroughs to ft.  mark it as a control flow merge.
+		if( ft && is_in_container(found_fallthrough_to, ft))
+			targets.insert(ft);
+		
+		// if there is a ft, mark that we've seen it now.	
+		if(ft)
+			found_fallthrough_to.insert(ft);
+		
+	}
+
+	return targets;
+}
+
+ControlFlowGraph_t::ControlFlowGraph_t(IRDB_SDK::Function_t* func) :
+	entry(NULL), function(dynamic_cast<Function_t*>(func))
+{
+	Build(func);	
+}
+
+
+void ControlFlowGraph_t::alloc_blocks(const IRDB_SDK::InstructionSet_t &starts, map<IRDB_SDK::Instruction_t*,BasicBlock_t*>& insn2block_map)
+{
+	/* create a basic block for each instruction that starts a block */
+	for(const auto &insn : starts)
+	{
+		if(is_in_container(insn2block_map,insn)) // already allocated 
+			continue;
+
+		auto  newblock=new BasicBlock_t;
+
+		assert( insn && newblock );
+
+		blocks.insert(newblock);
+		insn2block_map[insn]=newblock;
+	}
+}
+
+void ControlFlowGraph_t::build_blocks(const map<IRDB_SDK::Instruction_t*,BasicBlock_t*>& insn2block_map)
+{
+
+	/* Ask the basic block to set the fields for each block that need to be set */
+	for(const auto &it : insn2block_map)
+	{
+		const auto insn=it.first;
+		const auto block=it.second;
+
+		if(block->getInstructions().size()>0) // already built
+			continue;
+
+		assert(insn && block);
+
+		block->BuildBlock(insn, insn2block_map);
+
+	}
+
+}
+
+void ControlFlowGraph_t::find_unblocked_instructions(IRDB_SDK::InstructionSet_t &starts, IRDB_SDK::Function_t* func)
+{
+	auto mapped_instructions=InstructionSet_t();
+	auto missed_instructions=InstructionSet_t();
+	for(const auto block : GetBlocks())
+		mapped_instructions.insert(ALLOF(block->getInstructions()));
+
+	auto my_inserter=inserter(missed_instructions,missed_instructions.end());
+	set_difference(ALLOF(func->getInstructions()), ALLOF(mapped_instructions), my_inserter);
+	starts.insert(ALLOF(missed_instructions));
+}
+
+
+
+void ControlFlowGraph_t::Build(IRDB_SDK::Function_t* func)
+{
+	auto starts=FindBlockStarts(func);
+
+	auto insn2block_map=map<IRDB_SDK::Instruction_t*,BasicBlock_t*> ();
+
+	alloc_blocks(starts, insn2block_map);
+	build_blocks(insn2block_map);
+	/* record the entry block */
+	if(func->getEntryPoint())
+		entry=insn2block_map[func->getEntryPoint()];
+
+	/* most functions are done now. */
+	/* however, if a function has a (direct) side entrance, 
+	 * some code may appear unreachable and not be placed in 
+	 * a block -- here, we detect that code and create a 
+	 * new basic block for every instruction, as any may have a side entrance
+	 */ 
+	/* note:  side entrances may miss a block start */
+	/* in code that appears reachable from the entrance?! */
+	find_unblocked_instructions(starts, func);
+	alloc_blocks(starts, insn2block_map);
+	build_blocks(insn2block_map);
+}
+
+// returns true iff there's an edge from <p_src> to <p_tgt> in the CFG
+bool ControlFlowGraph_t::hasEdge(IRDB_SDK::BasicBlock_t *p_src, IRDB_SDK::BasicBlock_t *p_tgt) const
+{
+	const auto src_exists = blocks.find(p_src) != blocks.end();
+	const auto tgt_exists = blocks.find(p_tgt) != blocks.end();
+
+	if (!src_exists || !tgt_exists) return false;
+
+	const auto successors = p_src->getSuccessors();
+	return successors.find(p_tgt) != successors.end();
+}
+
+IRDB_SDK::CFGEdgeType_t ControlFlowGraph_t::getEdgeType(const IRDB_SDK::BasicBlock_t *p_src, const IRDB_SDK::BasicBlock_t *p_tgt) const
+{
+	const auto last_in_src = p_src->getInstructions()[p_src->getInstructions().size()-1];
+	const auto first_in_tgt = p_tgt->getInstructions()[0];
+
+	auto edgeType = IRDB_SDK::CFGEdgeType_t();
+
+	if (last_in_src->getFallthrough() == first_in_tgt)
+	{
+		edgeType.insert(IRDB_SDK::cetFallthroughEdge);
+	}
+
+	if (last_in_src->getTarget() == first_in_tgt)
+	{
+		edgeType.insert(IRDB_SDK::cetTargetEdge);
+	}
+
+	if (edgeType.size() == 0)
+	{
+		edgeType.insert(IRDB_SDK::cetIndirectEdge);
+	}
+
+	return edgeType;
+}
+
+/*
+ *  output operator
+ */
+ostream& IRDB_SDK::operator<<(ostream& os, const IRDB_SDK::ControlFlowGraph_t& cfg)
+{
+	cfg.dump(os);
+	return os;
+}
+
+void ControlFlowGraph_t::dump(ostream& os) const
+{
+	int i=0;
+
+	auto blk_numbers = map<IRDB_SDK::BasicBlock_t*,int>();
+	for(auto blk : getBlocks() ) 
+	{
+			blk_numbers[blk]=i++;
+	}
+	
+
+	for(auto block : getBlocks())
+	{
+		if(block==getEntry())
+			os<<"**** Entry    ";
+		else
+			os<<"---- NotEntry ";
+		os<<"block "<<std::dec<<blk_numbers[block]<<endl;
+		os<<"Successors: ";
+		for(auto succ : block->getSuccessors())
+		{
+			os<<blk_numbers[succ]<<", ";
+			
+		};
+		os<<endl;
+		os<<"Predecessors: ";
+		for(auto pred : block->getPredecessors())
+		{
+			os<<blk_numbers[pred]<<", ";
+		};
+		os<<endl;
+		os << *block;
+	}
+
+}
+
+unique_ptr<IRDB_SDK::ControlFlowGraph_t> IRDB_SDK::ControlFlowGraph_t::factory(IRDB_SDK::Function_t* func)
+{
+	return unique_ptr<IRDB_SDK::ControlFlowGraph_t>(new libIRDB::ControlFlowGraph_t(func));
+}
+
diff --git a/irdb-lib/libIRDB-cfg/src/Makefile b/irdb-lib/libIRDB-cfg/src/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..1554e4568c28be8e1ed93df0374692ad10825ff9
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/Makefile
@@ -0,0 +1,15 @@
+
+LIB=../../lib/libIRDB-cfg.a
+
+OBJS=BasicBlock.o CFG.o callgraph.o
+
+all: $(OBJS)
+
+$(OBJS): ../../include/core/*.hpp ../../include/cfg/*.hpp ../../include/*.hpp 
+
+clean:
+	rm -f $(OBJS)
+
+.cpp.o:
+	$(CXX) -fPIC -g -c -I. -I../../include -I../../../beaengine/include $<
+	ar rc $(LIB) $@
diff --git a/irdb-lib/libIRDB-cfg/src/SConscript b/irdb-lib/libIRDB-cfg/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..cb08c53f8c8a1a5c37f4e1c1247a591fdda427e5
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/SConscript
@@ -0,0 +1,31 @@
+import os
+
+Import('env')
+
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+libname="irdb-cfg"
+files=  '''
+	BasicBlock.cpp  callgraph.cpp  CFG.cpp domgraph.cpp criticaledge.cpp
+	'''
+cpppath=''' 
+	$IRDB_SDK/include/
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-core/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-cfg/include/
+	'''
+libpath='''
+	$SECURITY_TRANSFORMS_HOME/lib
+	'''
+
+myenv.Append(CCFLAGS=" -Wall -std=c++11 -fmax-errors=2 ")
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+lib=myenv.SharedLibrary(libname, Split(files), LIBS=Split("irdb-core"), LIBPATH=Split(libpath))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libIRDB-cfg/src/SConstruct b/irdb-lib/libIRDB-cfg/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b3bd01322f2b78089fd86e0e9b0ae01897c9c8a5
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+Return('lib')
diff --git a/irdb-lib/libIRDB-cfg/src/callgraph.cpp b/irdb-lib/libIRDB-cfg/src/callgraph.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..fe35a0105a294f1971f6003828827de5994f3c0a
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/callgraph.cpp
@@ -0,0 +1,297 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <map>
+#include <ostream>
+#include <libIRDB-core.hpp>
+#include <libIRDB-cfg.hpp>
+#include <irdb-util>
+
+using namespace libIRDB;
+using namespace std;
+
+
+Callgraph_t::Callgraph_t() : 
+	default_hellnode(NULL)
+{
+}
+
+unique_ptr<IRDB_SDK::CallGraph_t>  IRDB_SDK::CallGraph_t::factory(FileIR_t* const firp)
+{
+	auto ret=unique_ptr<IRDB_SDK::CallGraph_t>(new libIRDB::Callgraph_t());
+	if(firp != nullptr)
+		ret->addFile(firp);
+	return ret;
+}
+
+
+Callgraph_t::~Callgraph_t()
+{
+	for (auto p : nodes)
+	{
+		delete p.second;
+	}
+	nodes.clear();
+}
+
+static bool IsCallSite(Instruction_t* insn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+	return d->isCall();
+}
+
+static bool IsTailJmpSite(Instruction_t* insn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+	if(d->isBranch())
+		return false;
+
+	if(insn->getTarget()==NULL)
+		return true;
+
+	if(insn->getFunction() != insn->getTarget()->getFunction())
+		return true;
+	return false;
+}
+
+static bool IsPushJmpSite(Instruction_t* insn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+	if(d->getMnemonic()!="push" || insn->getFallthrough()==NULL)
+		return false;
+
+	if(insn->getRelocations().size()==0)
+		return false;
+
+	const auto d2=DecodedInstruction_t::factory(insn->getFallthrough());
+	if(!d2->isBranch())
+		return false;
+
+	return true;
+}
+
+void Callgraph_t::MarkCallSite(IRDB_SDK::Instruction_t* insn)
+{
+	auto from_func=insn->getFunction();
+	auto to_insn=insn->getTarget();
+	auto to_func= to_insn==NULL? NULL : to_insn->getFunction();
+
+	auto from_node = findNode(from_func);
+	auto to_node = findNode(to_func);
+
+	if (!from_node)
+		from_node = &GetDefaultHellNode();
+
+	if (!to_node)
+		to_node = &GetDefaultHellNode();
+
+	call_sites[from_node].insert(insn);
+	callees[from_node].insert(to_node);
+	callers[to_node].insert(from_node);
+}
+
+void Callgraph_t::CreateNodes(IRDB_SDK::FileIR_t *firp)
+{
+	const FunctionSet_t &fns=firp->getFunctions();
+	for(auto it=fns.begin(); fns.end() != it; ++it)
+	{
+		auto fn=*it;
+		if (fn) {
+			auto newnode = new CallGraphNode_t(fn);
+			nodes[fn] = newnode;
+//			cout << "Added CGNode: " << GetNodeName(newnode) << endl;
+		}
+	}
+}
+
+void Callgraph_t::addFile(IRDB_SDK::FileIR_t* const firp)
+{
+	// Create CG Nodes from functions
+	CreateNodes(firp);
+
+	// for each instruction 
+	auto &insns=firp->getInstructions();
+
+	for(auto it=insns.begin(); insns.end() != it; ++it)
+	{
+		auto insn=dynamic_cast<Instruction_t*>(*it);
+		if(IsCallSite(insn) || IsTailJmpSite(insn))
+			MarkCallSite(insn);
+		if(IsPushJmpSite(insn))
+			MarkCallSite(dynamic_cast<Instruction_t*>(insn->getFallthrough()));
+
+		if(insn->getFunction() && insn->getFunction()->getEntryPoint()==insn
+			&& insn->getIndirectBranchTargetAddress())
+		{
+				auto node = findNode(insn->getFunction());
+				assert(node);
+				callees[&GetDefaultHellNode()].insert(node);
+				callers[node].insert(&GetDefaultHellNode());
+		}
+	}
+}
+
+
+void Callgraph_t::_GetAncestors(IRDB_SDK::CallGraphNode_t* const node, IRDB_SDK::CallGraphNodeSet_t &ancestors, IRDB_SDK::CallGraphNodeSet_t &visited, bool skipHellNode) const
+{
+	if (!node || visited.count(node) > 0)
+		return;
+
+	cerr << "visiting node: " << GetNodeName(node) << " visited(size):" << visited.size() << endl;
+
+        // ancestor-traversal(node X)
+        //    mark X visited
+        //    get parents P of X
+        //    if P[i] not visited:
+        //         add P[i] to ancestors
+        //         ancestor-traversal(P[i])
+
+	visited.insert(node);
+
+	const auto &directPredecessors = getCallersOfNode(node);
+	for (const auto pred : directPredecessors ) // it = directPredecessors.begin(); it != directPredecessors.end(); ++it)
+	{
+		if (visited.count(pred) == 0)
+		{
+			assert(pred);
+			if (pred->isHellnode() && skipHellNode) continue;
+
+			cerr << "adding " << GetNodeName(pred) << " to ancestor list " << hex << pred << dec << endl;
+			ancestors.insert(pred);
+			_GetAncestors(pred, ancestors, visited, skipHellNode);
+		}
+	}
+}
+
+IRDB_SDK::CallGraphNode_t* Callgraph_t::findNode(IRDB_SDK::Function_t* const fn) const
+{
+	auto node_it=nodes.find(fn);
+	return (node_it==nodes.end()) ? nullptr : node_it->second;
+}
+
+void Callgraph_t::GetAncestors(IRDB_SDK::Function_t* const fn, IRDB_SDK::CallGraphNodeSet_t &ancestors, bool skipHellNode) const
+{
+	auto node = findNode(fn);
+	if (node)
+		GetAncestors(node, ancestors, skipHellNode);
+}
+
+void Callgraph_t::GetAncestors(IRDB_SDK::CallGraphNode_t* const node, IRDB_SDK::CallGraphNodeSet_t &ancestors, bool skipHellNode) const
+{
+	auto visited=IRDB_SDK::CallGraphNodeSet_t();
+	_GetAncestors(node, ancestors, visited, skipHellNode);
+}
+
+bool Callgraph_t::isReachable(IRDB_SDK::CallGraphNode_t* const from, IRDB_SDK::CallGraphNode_t* const to, bool skipHellNode) const
+{
+	auto ancestors=IRDB_SDK::CallGraphNodeSet_t();
+	GetAncestors(to, ancestors, skipHellNode);
+	return (ancestors.count(from) > 0);
+}
+
+void Callgraph_t::dump(std::ostream& fout) const
+{
+
+	fout<<"Dumping callgraph ..."<<endl;
+
+	fout<<"Mapping one way ..."<<endl;
+	for(const auto p : callees) // it=callees.begin(); callees.end()!=it; ++it)
+	{
+		// CallGraphNode_t* node = it->first;
+		// CallGraphNodeSet_t &node_callers=it->second;
+		const auto  node        =p.first;
+		const auto &node_callers=p.second;
+
+		fout<<"Function "<<GetNodeName(node)<<" calls: ";
+		for(const auto &the_callee : node_callers) // auto it2=node_callers.begin(); node_callers.end()!=it2; ++it2)
+		{
+			// CallGraphNode_t* the_callee=*it2;
+			fout<<GetNodeName(the_callee)<<", ";
+		}
+		fout<<endl;
+		for(const auto the_call_site : GetCallSites(node)) // auto it2=GetCallSites(node).begin(); GetCallSites(node).end() != it2; ++it2)
+		{
+			// CallSite_t the_call_site=*it2;
+			fout<<"\t"<<GetCallsiteDisassembly(the_call_site)<<endl;
+		}
+	}
+
+	fout<<"Mapping the other way ..."<<endl;
+	for(const auto p : callers) // auto it=callers.begin(); callers.end()!=it; ++it)
+	{
+		// CallGraphNode_t* n=it->first;
+		const auto  n           =p.first;
+		const auto &node_callees=p.second;
+
+		fout<<"Function "<<GetNodeName(n)<<" called by: ";
+		for(auto the_caller : node_callees) // CallGraphNodeSet_t::iterator it2=node_callees.begin(); node_callees.end()!=it2; ++it2)
+		{
+			// CallGraphNode_t* the_caller=*it2;
+			fout<<GetNodeName(the_caller)<<", ";
+
+		}
+		fout<<endl;
+	}
+
+
+	fout<<"Printing call sites..."<<endl;
+	for(const auto p : call_sites) // auto it=call_sites.begin(); call_sites.end()!=it; ++it)
+	{
+		const auto from_node=p.first;
+		const auto &call_sites_for_func=p.second;
+
+		fout<<"Call Sites for "<<GetNodeName(from_node)<<": ";
+
+		for(const auto the_call_site : call_sites_for_func) // auto it2=call_sites_for_func.begin(); call_sites_for_func.end() != it2; ++it2)
+		{
+			// auto the_call_site=*it2;
+			fout<<GetCallsiteDisassembly(the_call_site)<<", ";
+		}
+		fout<<endl;
+	}
+
+	fout<<"Done!"<<endl;
+}
+
+void CallGraphNode_t::dump(std::ostream& fout) const
+{
+	if (isHellnode()) 
+	{
+		fout << "HELLNODE" << GetHellNodeType();
+	} 
+	else 
+	{
+		assert(getFunction());
+		fout << getFunction()->getName();
+	}
+}
+
+ostream& IRDB_SDK::operator<<(ostream& os, const IRDB_SDK::CallGraph_t& cg)
+{
+	cg.dump(os);
+	return os;
+}
+ostream& IRDB_SDK::operator<<(ostream& os, const IRDB_SDK::CallGraphNode_t& cgn)
+{
+	cgn.dump(os);
+	return os;
+}
+
diff --git a/irdb-lib/libIRDB-cfg/src/criticaledge.cpp b/irdb-lib/libIRDB-cfg/src/criticaledge.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..82e5dd67edee08cfc8744ab42e7a57bc40dabbda
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/criticaledge.cpp
@@ -0,0 +1,100 @@
+/*
+ * Copyright (c) 2019 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <libIRDB-cfg.hpp>
+#include <irdb-util>
+#include <algorithm>
+
+using namespace std;
+using namespace libIRDB;
+
+#define ALLOF(a) begin(a),end(a)
+
+CriticalEdgeAnalyzer_t::CriticalEdgeAnalyzer_t(const ControlFlowGraph_t* p_cfg, const bool p_conservative) :
+	m_cfg(p_cfg),
+	m_conservative(p_conservative)
+{
+	init();
+}
+
+/*
+*   Critical edge between two nodes is where the source node has multiple successsors,
+*   and the target node has multiple predecessors 
+*/
+void CriticalEdgeAnalyzer_t::init()
+{
+	for (const auto &src : m_cfg->getBlocks())
+	{
+		auto num_successors = src->getSuccessors().size();
+		if (!m_conservative)
+		{
+			// in aggressive (non conservative) mode, ignore indirect edges
+			// when counting number of successors
+			num_successors = count_if
+				(
+					ALLOF(src->getSuccessors()),
+					[&] (const IRDB_SDK::BasicBlock_t* bb_tgt) 
+					{
+						auto myEdgeType = m_cfg->getEdgeType(src, bb_tgt);
+						return myEdgeType.find(IRDB_SDK::cetTargetEdge)!=myEdgeType.end() || 
+						       myEdgeType.find(IRDB_SDK::cetFallthroughEdge)!=myEdgeType.end();
+					}
+				);
+		}
+
+		if (num_successors <= 1) continue;
+
+		for (const auto &tgt : src->getSuccessors())
+		{
+			auto num_predecessors = tgt->getPredecessors().size();
+			if (!m_conservative)
+			{
+				// in aggressive (non conservative) mode, ignore indirect edges
+				// when counting number of predecessors
+				num_predecessors = count_if
+					(
+						ALLOF(tgt->getPredecessors()),
+						[&] (const IRDB_SDK::BasicBlock_t* bb_pred) 
+						{
+							auto myEdgeType = m_cfg->getEdgeType(bb_pred, tgt);
+							return myEdgeType.find(IRDB_SDK::cetTargetEdge)!=myEdgeType.end() || 
+							       myEdgeType.find(IRDB_SDK::cetFallthroughEdge)!=myEdgeType.end();
+						}
+					);
+			}
+
+			if (num_predecessors > 1)
+			{
+				auto e=IRDB_SDK::BasicBlockEdge_t(src, tgt);
+				criticals.insert(e);
+			}
+		}
+	}
+}
+
+unique_ptr<IRDB_SDK::CriticalEdges_t> IRDB_SDK::CriticalEdges_t::factory(
+	const IRDB_SDK::ControlFlowGraph_t &p_cfg, 
+	const bool p_conservative)
+{
+	auto real_cfg = dynamic_cast<const libIRDB::ControlFlowGraph_t*>(&p_cfg);
+	return unique_ptr<IRDB_SDK::CriticalEdges_t>(new libIRDB::CriticalEdgeAnalyzer_t(
+				real_cfg, p_conservative));
+}
diff --git a/irdb-lib/libIRDB-cfg/src/domgraph.cpp b/irdb-lib/libIRDB-cfg/src/domgraph.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..36a10b4ced1dca25f7a867d268b8032bdaf44584
--- /dev/null
+++ b/irdb-lib/libIRDB-cfg/src/domgraph.cpp
@@ -0,0 +1,400 @@
+
+#include <libIRDB-cfg.hpp>
+#include <algorithm>
+#include <irdb-util>
+#include <irdb-cfg>
+#include <memory>
+
+
+using namespace std;
+using namespace libIRDB;
+
+#define ALLOF(a) begin((a)), end((a))
+
+/*
+ * is_in_container - a handle template function returning whether key S is contained in container T.
+ */
+template <class T, class S>
+inline bool is_in_container(const T& container, const S& key)
+{
+        bool is_in=container.find(key) != container.end();
+        return is_in;
+}
+
+template <class S>
+inline bool is_in_set(const std::set<S>& container, const S& key)
+{
+        return std::find(container.begin(), container.end(), key) != container.end();
+}
+/*
+ * find_map_object - without modifying the object, return the element
+ */
+template <class T, class S>
+inline S const& find_map_object( const std::map< T , S > &a_map, const T& key)
+{
+        const auto it=a_map.find(key);
+        assert(it!=a_map.end());
+
+        return (*it).second;
+}
+
+
+
+// constructor 
+DominatorGraph_t::DominatorGraph_t(const ControlFlowGraph_t* p_cfg, bool needs_postdoms, bool needs_idoms)
+	: cfg(*p_cfg), warn(false)
+{
+	auto &blocks=p_cfg->getBlocks();
+
+
+	assert(needs_postdoms==false);
+	assert(needs_idoms==false);
+
+
+	pred_func_ptr_t func_get_predecessors=[](const IRDB_SDK::BasicBlock_t* node) -> const IRDB_SDK::BasicBlockSet_t&
+	{
+		return node->getPredecessors();
+	};
+
+	dom_graph=Dom_Comp(blocks, func_get_predecessors, p_cfg->getEntry());
+	idom_graph=Idom_Comp(blocks, dom_graph, p_cfg->getEntry());
+
+	Dominated_Compute();
+
+// a func may have multiple exit nodes.  how do we deal with that?
+// psuedo-block?  invoke this for each exit block?
+//	pred_func_ptr_t func_get_successors=[](const BasicBlock_t* node) -> const BasicBlockSet_t&
+//	{
+//		return node->GetSuccessors();
+//	};
+//	post_dom_graph=Dom_Comp(p_cfg->GetBlocks(), func_get_successors, p_cfg->GetEntry());
+//	post_idom_graph=IDom_Comp(p_cfg->GetBlocks(), post_dom_graph, p_cfg->GetEntry());
+}
+
+
+
+
+/*
+
+algorithm from advanced compiler design & impelmentation, Mucnick, 2nd edition page 18
+
+procedure Dom_Comp(N,Pred,r) returns Node-> set of Node
+	N: in set of Node
+	Pred: in Node -> set of Node
+	r: in Node
+	D, T: set of Node
+	n, p: Node
+	change := true: boolean
+	Domin: Node -> set of Node
+	Domin(r) := { r } 
+
+	for each n \in N - {r} do
+		Domin(n)={N}
+	od
+	repeat
+		change := false
+		for each n \in N - {r} do		
+
+			T := N
+			for each p \in Pred(n) do
+				T = T intersect Domin(p)
+			done
+			D = {n} union T
+			if D != Domin(n) then
+				change := true
+				Domin(n) := D
+			fi
+		done
+	until ! change
+	return Domin
+end || Dom_Comp
+
+*/
+
+DominatorMap_t DominatorGraph_t::Dom_Comp(const IRDB_SDK::BasicBlockSet_t& N, pred_func_ptr_t get_preds,  IRDB_SDK::BasicBlock_t* r)
+{
+/*
+	D, T: set of Node
+	n, p: Node
+	change := true: boolean
+	Domin: Node -> set of Node
+	Domin(r) := { r } 
+*/
+	IRDB_SDK::BasicBlockSet_t D, T;
+	bool change=true;
+	DominatorMap_t Domin;
+	Domin[r].insert(r);
+
+	IRDB_SDK::BasicBlockSet_t NminusR=N;
+	NminusR.erase(r);
+
+/*
+	for each n \in N - {r} do
+		Domin(n)={N}
+	od
+*/
+	for( auto n : NminusR)
+	{
+		Domin[n]=N;
+	};
+
+/* 
+	repeat
+*/	
+	do
+	{
+		change = false;
+		/*
+		for each n \in N - {r} do		
+		*/
+		for( auto n : NminusR)
+		{
+			/* T := N */
+			T=N;
+/*
+
+			for each p \in Pred(n) do
+				T = T intersect Domin(p)
+			done
+*/
+			for(auto p : get_preds(n) )
+			{
+				IRDB_SDK::BasicBlockSet_t tmp;
+				set_intersection(T.begin(), T.end(), Domin[p].begin(), Domin[p].end(), inserter(tmp,tmp.begin()));
+				T=tmp;
+				
+			};
+			/*
+			D = {n} union T
+			*/
+			D=T;
+			D.insert(n);
+
+			/*
+			if D != Domin(n) then
+				change := true
+				Domin(n) := D
+			fi
+			*/
+			if(D != Domin[n])
+			{
+				change=true;	// keep trying
+				Domin[n]=D;
+			}
+		};
+/*
+		done
+	until ! change
+*/
+	}
+	while (  change );
+
+
+// log output
+#if 0
+
+                for_each(N.begin(), N.end(), [&](const BasicBlock_t* blk)
+                {
+                        assert(blk);
+                        const BasicBlockSet_t& blk_dominates=Domin[blk];
+                        Instruction_t* first_insn=*(blk->getInstructions().begin());
+                        assert(first_insn);
+#if 1
+                        cout<<"\tBlock " <<endl<<*blk<<endl;
+                        
+#endif
+                        cout<<"\t Dominated by:"<<endl;
+                        for_each(blk_dominates.begin(), blk_dominates.end(), [&](const BasicBlock_t* dom_blk)
+                        {
+                                cout<<*dom_blk<<endl;
+                        });
+                });
+#endif
+	return Domin;
+}
+
+
+
+/* algorith for constructing immediate dominators from Muchnick, page 184.
+
+procedure Idom_Comp(N,Domin,r) returns Node -> Node
+	N: in set of Node
+	Domin: in Node -> set of Node
+	r: in Node
+begin
+	n, s, t: Node
+	Tmp: Node -> set of Node
+	IDom: Node->Node
+	for each n \in N do
+		Tmp(n) := Domin(n) - {n} 
+	od
+
+	for each n \in N - {r} do
+		for each s \in Tmp(n) do
+			for each t \in Tmp(n) - {s}  do
+				if t \in Tmp(s) then
+					Tmp(n) -= {t}
+				fi
+			od
+		od
+	od
+
+	for each n \in N-{r} do
+		IDom(n) = <only element in>Tmp(n)
+	od
+	return IDdom
+end || IDom_Comp
+*/
+	
+
+
+BlockToBlockMap_t DominatorGraph_t::Idom_Comp(const IRDB_SDK::BasicBlockSet_t& N, const DominatorMap_t &Domin, IRDB_SDK::BasicBlock_t* r) 
+{
+	// n, s, t: Node
+	//BasicBlock_t* n=NULL, *s=NULL, *t=NULL;
+
+	// Tmp: Node -> set of Node
+	DominatorMap_t Tmp;
+	
+	// IDom: Node->Node
+	BlockToBlockMap_t IDom;
+
+
+	// calculate this set as we use it several times
+	IRDB_SDK::BasicBlockSet_t NminusR = N;
+	NminusR.erase(r);
+
+
+	// for each n \in N do
+	for(auto n : N)
+	{
+		//Tmp(n) := Domin(n) - {n} 
+		Tmp[n] = Domin.at(n);
+		Tmp[n].erase(n);
+	// od
+	};
+
+
+	//for each n \in N - {r} do
+	for(auto n : NminusR)
+	{
+		// for each s \in Tmp(n) do
+		auto Tmp_n=Tmp[n];
+		// for_each( Tmp_n.begin(), Tmp_n.end(), [&]( BasicBlock_t* s)
+		for (auto s : Tmp_n)
+		{
+
+			//for each t \in Tmp(n) - {s}  do
+			// for_each( Tmp_n.begin(), Tmp_n.end(), [&]( BasicBlock_t* t)
+			for (auto t : Tmp_n)
+			{
+				// quickly do Tmp(n)-s 
+				if(t != s)   
+				{
+					//if t \in Tmp(s) then
+					if( is_in_container(Tmp[s],t))
+					{
+						//Tmp(n) -= {t}
+						Tmp[n].erase(t);
+					}
+				}
+			};
+		};
+	};
+
+
+	//for each n \in N-{r} do
+	for (auto n : NminusR)
+	{
+		//IDom(n) = <only element in>Tmp(n)
+		IDom[n]= *(Tmp[n].begin());
+		if(Tmp[n].size()!=1)	// should only be one idominator.
+			warn=true;
+	};
+	return IDom;
+} // IDom_Comp
+
+
+void DominatorGraph_t::Dominated_Compute()
+{
+	for(auto p : dom_graph)
+	{
+		auto dominates     = p.first;
+		auto dominated_set = p.second;
+
+		for(auto dominated : dominated_set)
+			dominated_graph[dominated].insert(dominates);
+	}
+	for(auto p : idom_graph)
+	{
+		auto dominates = p.first;
+		auto dominated = p.second;
+		idominated_graph[dominated].insert(dominates);
+	}
+
+}
+
+
+
+
+ostream& IRDB_SDK::operator<<(ostream& os, const DominatorGraph_t& dg)
+{
+	dg.dump(os);
+	return os;
+}
+
+void DominatorGraph_t::dump(ostream& os) const
+{
+	for(auto blk : cfg.getBlocks())
+	{
+		assert(blk);
+		const auto& blk_dominators=getDominators(blk);
+		auto first_insn=*(blk->getInstructions().begin());
+		assert(first_insn);
+
+		os<<"\tBlock entry id:" <<dec<<blk->getInstructions()[0]->getBaseID()<<endl;
+		os<<"\t\tBlocks that (eventually) dominate me: ";
+		for(auto blk : blk_dominators)
+		{
+			os<<blk->getInstructions()[0]->getBaseID()<<", ";
+		};
+		os<<endl;
+
+		const IRDB_SDK::BasicBlock_t* idom=getImmediateDominator(blk);
+		if(idom)
+			os<<"\t\tMy Immediate Dominator: "<<dec<<idom->getInstructions()[0]->getBaseID()<<endl;
+		else
+			os<<"\t\tNo Immed Dominator."<<endl;
+
+
+		os<<"\t\tBlocks I (eventually) Dominate: ";
+		const auto& dominated_blocks=getDominated(blk);
+		for(auto blk : dominated_blocks)
+		{
+			os<<blk->getInstructions()[0]->getBaseID()<<", ";
+		};
+		os<<endl;
+
+		os<<"\t\tBlocks I Immediately Dominate: ";
+		const auto& imm_dominated_blocks=getImmediateDominated(blk);
+		for(auto blk : imm_dominated_blocks)
+		{
+			os<<blk->getInstructions()[0]->getBaseID()<<", ";
+		};
+		os<<endl;
+	};
+
+}
+
+// constructor 
+unique_ptr<IRDB_SDK::DominatorGraph_t>
+IRDB_SDK::DominatorGraph_t::factory(const ControlFlowGraph_t* p_cfg, const bool needs_postdoms, const bool needs_idoms)
+{
+	const auto real_cfg=dynamic_cast<const libIRDB::ControlFlowGraph_t*>(p_cfg);
+	return unique_ptr<IRDB_SDK::DominatorGraph_t>(new libIRDB::DominatorGraph_t(real_cfg, needs_postdoms, needs_idoms));
+}
+
+
+
+
+
diff --git a/irdb-lib/libIRDB-core/include/IRDB_Objects.hpp b/irdb-lib/libIRDB-core/include/IRDB_Objects.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..aaa34b8abebcf01c0e43be4a2025c9122828aea4
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/IRDB_Objects.hpp
@@ -0,0 +1,76 @@
+#ifndef IRDB_Objects_h
+#define IRDB_Objects_h
+
+namespace libIRDB
+{
+
+// TODO: Should really use unordered maps but was getting build errors
+
+
+// *** A toolchain step should NOT delete pointers to any variant, file IR, or file object stored
+//     in a IRFiles_t object. I have made pointers shared where possible to communicate this. ***
+class IRDBObjects_t : virtual public IRDB_SDK::IRDBObjects_t
+{
+	public:
+		IRDBObjects_t() 
+                {
+			pqxx_interface = std::unique_ptr<pqxxDB_t>(new pqxxDB_t());
+			// set up interface to the sql server
+			BaseObj_t::setInterface(pqxx_interface.get());
+                };
+		virtual ~IRDBObjects_t();
+
+		// Add/delete file IRs for a variant.
+		// Step does not have ownership of fileIR (can't make assumptions about its
+		// lifetime!), and a call to DeleteFileIR will render any pointers to that fileIR dangling.            
+		// AddFileIR returns the added IR or the preexistent IR if it was already added.
+		IRDB_SDK::FileIR_t* addFileIR(const IRDB_SDK::DatabaseID_t variant_id, const IRDB_SDK::DatabaseID_t file_id);    // Returns NULL if no such file exists
+		void deleteFileIR(const IRDB_SDK::DatabaseID_t file_id);
+                // Add or delete a variant
+                // Step does not have ownership of variant (can't make assumptions about its lifetime!), and a call to DeleteVariant will render any pointers to that variant dangling.
+                // Deleting a variant does NOT write its files' IRs, but DOES delete them!
+                // AddVariant returns the added variant or the preexistent variant if it was already added.
+		IRDB_SDK::VariantID_t* addVariant(const IRDB_SDK::DatabaseID_t variant_id);
+                void deleteVariant(IRDB_SDK::DatabaseID_t variant_id);
+                
+                // Get DB interface
+		IRDB_SDK::pqxxDB_t* getDBInterface() const;
+		IRDB_SDK::pqxxDB_t* resetDBInterface();
+
+		// Write back variants and file IRs. Does NOT commit changes.
+                int writeBackFileIR(const IRDB_SDK::DatabaseID_t file_id, std::ostream *verbose_logging=nullptr);
+                int writeBackVariant(const IRDB_SDK::DatabaseID_t variant_id);   // Does NOT write back its files' IRs
+		int writeBackAll(std::ostream* verbose_logging=nullptr);    // Returns -1 if any writes fail.
+                
+                void deleteAll(void);
+
+		void tidyIR();
+		
+	private:
+                std::unique_ptr<pqxxDB_t> pqxx_interface;
+		// type aliases of maps. maps allow speed of finding needed files, file IRs 
+		// and/or variants that have already been read from the DB 
+		using IdToVariantMap_t = std::map<IRDB_SDK::DatabaseID_t, std::unique_ptr<VariantID_t>>; 
+		struct FileIRInfo_t
+		{
+  		    File_t * file;
+  		    std::unique_ptr<FileIR_t> fileIR;
+
+		    FileIRInfo_t() : file(nullptr), fileIR(nullptr)
+       		    {
+               	    } 
+
+		};
+		using IdToFileIRInfoMap_t = std::map<IRDB_SDK::DatabaseID_t, FileIRInfo_t>; 
+                
+		IdToVariantMap_t variant_map;
+        	IdToFileIRInfoMap_t file_IR_map;
+
+		// minor helper
+		bool filesAlreadyPresent(const FileSet_t&) const;
+                
+};
+
+ 
+}
+#endif
diff --git a/irdb-lib/libIRDB-core/include/address.hpp b/irdb-lib/libIRDB-core/include/address.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..f6b341b56c76e902a82f2a1a2a64e329e422d919
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/address.hpp
@@ -0,0 +1,72 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+
+//
+// An address in a variant.
+//
+using virtual_offset_t = IRDB_SDK::VirtualOffset_t;
+class AddressID_t : virtual public IRDB_SDK::AddressID_t, public BaseObj_t
+{
+    public:
+	virtual ~AddressID_t() {}
+	AddressID_t() : BaseObj_t(NULL), fileID(NOT_IN_DATABASE), virtual_offset(0) 
+		{ setBaseID(NOT_IN_DATABASE); }
+	AddressID_t(db_id_t myid, db_id_t myfileID, virtual_offset_t voff) : BaseObj_t(NULL), fileID(myfileID), virtual_offset(voff) 
+		{ setBaseID(myid); }
+
+	AddressID_t& operator=(const AddressID_t &rhs) {
+		if (this != &rhs)
+		{
+			this->fileID = rhs.fileID;	
+			this->virtual_offset = rhs.virtual_offset;	
+		}
+
+		return *this;
+ 	}
+
+        db_id_t getFileID() const { return fileID; }
+        void setFileID(db_id_t thefileID) { fileID=thefileID; }
+
+        virtual_offset_t getVirtualOffset() const { return virtual_offset; }
+        void setVirtualOffset(virtual_offset_t voff) { virtual_offset=voff; }
+
+	std::vector<std::string> WriteToDB(File_t *vid, db_id_t newid, bool p_withHeader);
+
+	bool operator<(const AddressID_t& cmp) const 
+		{ return fileID < cmp.fileID || (fileID == cmp.fileID && virtual_offset < cmp.virtual_offset);} 
+
+	bool operator!=(const AddressID_t& cmp) const 
+		{ return fileID != cmp.fileID || virtual_offset != cmp.virtual_offset; }  
+
+
+    private:
+        db_id_t fileID;          // The ID of the file
+        virtual_offset_t virtual_offset;  // the virtual address(offset) into the file. 
+                             // May be 0 if this insn doesn't exist
+                             // within a file.
+
+	void Register(VariantID_t *vid);
+
+};
+}
diff --git a/irdb-lib/libIRDB-core/include/archdesc.hpp b/irdb-lib/libIRDB-core/include/archdesc.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..e7299d450190a189b6929b41a957db00170aba93
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/archdesc.hpp
@@ -0,0 +1,51 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+
+using ADFileType_t    = IRDB_SDK::ADFileType_t;
+using ADMachineType_t = IRDB_SDK::ADMachineType_t;
+
+class ArchitectureDescription_t : virtual public IRDB_SDK::ArchitectureDescription_t
+{
+	public:
+
+		virtual ~ArchitectureDescription_t() {}
+		ArchitectureDescription_t() : bits(0), ft(IRDB_SDK::adftNone), mt(IRDB_SDK::admtNone) {}
+
+		int getBitWidth() const 		{ return bits; }	
+		void setBitWidth(const int _bits) 	{ bits=_bits; }	
+
+		ADFileType_t getFileType() const	{ return ft; }	
+		void setFileType(const ADFileType_t t) 	{ ft=t; }
+
+		ADMachineType_t getMachineType() const 		{ return mt; }	
+		void setMachineType(const ADMachineType_t t) 	{ mt=t; }
+
+	private:
+
+		size_t bits;
+		ADFileType_t ft;
+		ADMachineType_t mt;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/baseobj.hpp b/irdb-lib/libIRDB-core/include/baseobj.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..00abd21a166fbd056a3dd73b026e90be7a24d4da
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/baseobj.hpp
@@ -0,0 +1,63 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+namespace libIRDB
+{
+using virtual_offset_t = IRDB_SDK::VirtualOffset_t;
+using db_id_t          = IRDB_SDK::DatabaseID_t;
+using RelocationSet_t  = IRDB_SDK::RelocationSet_t;
+
+
+// A base class for something that all objects have, for now just a DOIP.
+// see .cpp file for method descriptions.
+class BaseObj_t : virtual public IRDB_SDK::BaseObj_t
+{
+    public:
+	virtual ~BaseObj_t() {}
+        BaseObj_t(doip_t* doip);
+
+        // static void SetInterface(DBinterface_t *dbintr);
+        static DBinterface_t* GetInterface() {return dbintr;}
+
+        // get and set the ID
+        db_id_t getBaseID() const {return base_id; }
+        db_id_t getDoipID() const { return doip ? doip->GetBaseID() : NOT_IN_DATABASE; }
+        void setDoipID(IRDB_SDK::Doip_t *dp)  { doip=dynamic_cast<doip_t*>(dp); if(dp) assert(doip);  }
+        void setBaseID(db_id_t id) {base_id=id; }
+
+	virtual RelocationSet_t& GetRelocations() { return relocs; }
+	virtual const RelocationSet_t& getRelocations() const { return relocs; }
+	virtual void setRelocations(const RelocationSet_t& rels) { relocs=rels; }
+
+
+    protected:
+        static DBinterface_t *dbintr;
+
+    private:
+        doip_t* doip;
+        db_id_t base_id;    // -1 means not yet in the DB.
+        RelocationSet_t relocs;
+
+	friend class IRDB_SDK::BaseObj_t;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/basetypes.hpp b/irdb-lib/libIRDB-core/include/basetypes.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..16cd27493835113a7569bd0514fd22da7f8f8860
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/basetypes.hpp
@@ -0,0 +1,55 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+namespace libIRDB
+{
+	using  virtual_offset_t = IRDB_SDK::VirtualOffset_t;
+	using  db_id_t = IRDB_SDK::DatabaseID_t;
+	using  schema_version_t = IRDB_SDK::SchemaVersionID_t;
+
+	// forward decls
+	class AddressID_t;
+	class ArchitectureDescription_t;
+   	class BaseObj_t;
+   	class DatabaseError_t;
+   	class DBinterface_t;
+   	class Doip_t;
+   	class EhProgram_t;
+   	class EhCallSite_t;
+   	class File_t;
+   	class FileIR_t;
+   	class Function_t;
+   	class ICFS_t;
+   	class Instruction_t;
+   	class IRDBObjects_t;
+   	class pqxxDB_t;
+   	class Relocation_t;
+   	class DataScoop_t;
+   	class Type_t;
+   	class BasicType_t;
+   	class PointerType_t;
+   	class AggregateType_t;
+   	class FuncType_t;
+   	class VariantID_t;
+	class DecodedInstructionDispatcher_t;
+ 	class DecodedOperandDispatcher_t;
+
+}
diff --git a/irdb-lib/libIRDB-core/include/dbinterface.hpp b/irdb-lib/libIRDB-core/include/dbinterface.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..fb4836ab16fc3cc460de37d18ae189d90ef55d92
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/dbinterface.hpp
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+using DatabaseErrorType_t = IRDB_SDK::DatabaseErrorType_t;
+
+class DatabaseError_t : virtual public IRDB_SDK::DatabaseError_t
+{
+	public: 
+		virtual ~DatabaseError_t() { }
+		DatabaseError_t(DatabaseErrorType_t the_err) : err(the_err) {}
+		DatabaseErrorType_t GetErrorCode() const { return err; }
+	private:
+		DatabaseError_t::DatabaseErrorType_t err;
+};
+
+std::ostream& operator<<(std::ostream& output, const DatabaseError_t& p);
+
+
+// an interface to a database
+class DBinterface_t : virtual public IRDB_SDK::DBinterface_t
+{
+	public:
+		DBinterface_t() {};
+		virtual ~DBinterface_t() {};
+                virtual void issueQuery(std::string query)=0;
+                virtual void moveToNextRow()=0;
+                virtual std::string getResultColumn(std::string colname)=0;
+                virtual bool isDone()=0;
+                virtual void commit()=0;
+
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/decode.hpp b/irdb-lib/libIRDB-core/include/decode.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..79bd8617f47f14d06db59b03894423b09e31c651
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/decode.hpp
@@ -0,0 +1,10 @@
+
+namespace libIRDB
+{
+
+using DecodedInstruction_t   = IRDB_SDK::DecodedInstruction_t;
+using DecodedOperand_t       = IRDB_SDK::DecodedOperand_t;
+using DecodedOperandVector_t = IRDB_SDK::DecodedOperandVector_t;
+
+}
+
diff --git a/irdb-lib/libIRDB-core/include/decode_base.hpp b/irdb-lib/libIRDB-core/include/decode_base.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..5cbbcee821ef04a9cd55e5784b3e512eeb5d27c6
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/decode_base.hpp
@@ -0,0 +1,50 @@
+#if 0
+namespace libIRDB
+{
+
+using namespace libIRDB;
+using namespace std;
+
+class DecodedOperandCapstone_t;
+
+class DecodedInstructionCapstone_t : virtual public IRDB_SDK::DecodedInstruction_t 
+{
+	public:
+		virtual ~DecodedInstructionCapstone_t(){}
+		virtual string getDisassembly() const =0;
+		virtual bool valid() const =0;
+		virtual uint32_t length() const =0;
+		virtual bool isBranch() const =0;
+		virtual bool isCall() const =0;
+		virtual bool isUnconditionalBranch() const =0;
+		virtual bool isConditionalBranch() const =0;
+		virtual bool isReturn() const =0;
+		virtual string getMnemonic() const =0;
+		virtual int64_t getImmediate() const =0;
+		virtual virtual_offset_t getAddress() const =0;
+		virtual bool setsStackPointer() const =0;
+		virtual uint32_t getPrefixCount() const =0;
+		virtual bool hasRelevantRepPrefix() const =0;
+		virtual bool hasRelevantRepnePrefix() const =0;
+		virtual bool hasRelevantOperandSizePrefix() const =0;
+		virtual bool hasRexWPrefix() const =0;
+		virtual bool hasImplicitlyModifiedRegs() const =0;
+		virtual virtual_offset_t getMemoryDisplacementOffset(const IRDB_SDK::DecodedOperand_t& t, const Instruction_t* insn) const =0;
+
+		// 0-based.  first operand is numbered 0.
+		virtual bool hasOperand(const int op_num) const =0;
+		virtual shared_ptr<IRDB_SDK::DecodedOperand_t> getOperand(const int op_num) const =0;
+		virtual DecodedOperandVector_t getOperands() const =0;
+
+	private:
+
+		// static unique_ptr<DecodedInstructionCapstone_t> factory(const Instruction_t* i);
+		// static unique_ptr<DecodedInstructionCapstone_t> factory(const IRDB_SDK::VirtualOffset_t start_addr, const void *data, uint32_t max_len);
+		// static unique_ptr<DecodedInstructionCapstone_t> factory(const IRDB_SDK::VirtualOffset_t start_addr, const void *data, const void* endptr);
+		// friend class DecodedInstructionDispatcher_t;
+
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libIRDB-core/include/decode_csarm.hpp b/irdb-lib/libIRDB-core/include/decode_csarm.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..b517d7d04b0708e317ee4a3809680866ff67bfff
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/decode_csarm.hpp
@@ -0,0 +1,72 @@
+
+namespace libIRDB
+{
+
+using namespace libIRDB;
+using namespace std;
+
+class DecodedOperandCapstoneARM64_t;
+class DecodedInstructionCapstoneARM64_t : virtual public IRDB_SDK::DecodedInstruction_t
+{
+	public:
+		DecodedInstructionCapstoneARM64_t()=delete;
+		DecodedInstructionCapstoneARM64_t& operator=(const DecodedInstructionCapstoneARM64_t& copy);
+
+		virtual ~DecodedInstructionCapstoneARM64_t();
+
+		virtual string getDisassembly() const override;
+		virtual bool valid() const override;
+		virtual uint32_t length() const override;
+		virtual bool isBranch() const override;
+		virtual bool isCall() const override;
+		virtual bool isUnconditionalBranch() const override; 
+		virtual bool isConditionalBranch() const override; 
+		virtual bool isReturn() const override; 
+		virtual string getMnemonic() const override; 
+		virtual int64_t getImmediate() const override; 
+		virtual virtual_offset_t getAddress() const override; 
+		virtual bool setsStackPointer() const override; 
+		virtual uint32_t getPrefixCount() const override; 
+		virtual bool hasRelevantRepPrefix() const override; 
+		virtual bool hasRelevantRepnePrefix() const override; 
+		virtual bool hasRelevantOperandSizePrefix() const override; 
+		virtual bool hasRexWPrefix() const override; 
+		virtual bool hasImplicitlyModifiedRegs() const override;
+ 		virtual IRDB_SDK::VirtualOffset_t getMemoryDisplacementOffset(const DecodedOperand_t* t, const IRDB_SDK::Instruction_t* insn) const override;
+
+		// 0-based.  first operand is numbered 0.
+		virtual bool hasOperand(const int op_num) const override;
+		virtual std::shared_ptr<DecodedOperand_t> getOperand(const int op_num) const override;
+		virtual DecodedOperandVector_t getOperands() const override;
+
+	private:
+
+		void Disassemble(const virtual_offset_t start_addr, const void *data, const uint32_t max_len);
+
+		shared_ptr<void> my_insn;
+
+		class CapstoneHandle_t
+		{
+			public:
+				CapstoneHandle_t(FileIR_t* firp=NULL);
+				inline unsigned long getHandle() { return handle; }
+
+			private:
+				// csh handle; // this is the real type, but it's an alias and I don't want to export capstone values.
+				unsigned long handle;
+		};
+		static CapstoneHandle_t *cs_handle;
+
+
+		friend class IRDB_SDK::DecodedInstruction_t;
+		friend class DecodedOperandCapstoneARM64_t;
+
+		DecodedInstructionCapstoneARM64_t(const shared_ptr<void> &my_insn);
+		DecodedInstructionCapstoneARM64_t(const Instruction_t*);
+		DecodedInstructionCapstoneARM64_t(const virtual_offset_t start_addr, const void *data, uint32_t max_len);
+		DecodedInstructionCapstoneARM64_t(const virtual_offset_t start_addr, const void *data, const void* endptr);
+		DecodedInstructionCapstoneARM64_t(const DecodedInstructionCapstoneARM64_t& copy);
+};
+
+}
+
diff --git a/irdb-lib/libIRDB-core/include/decode_csx86.hpp b/irdb-lib/libIRDB-core/include/decode_csx86.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..c7e85d91bb308db2b3d637c5a1d5cc28dcff73ee
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/decode_csx86.hpp
@@ -0,0 +1,72 @@
+
+namespace libIRDB
+{
+
+using namespace libIRDB;
+using namespace std;
+
+class DecodedOperandCapstoneX86_t;
+class DecodedInstructionCapstoneX86_t : virtual public DecodedInstruction_t
+{
+	public:
+		DecodedInstructionCapstoneX86_t()=delete;
+		DecodedInstructionCapstoneX86_t& operator=(const DecodedInstructionCapstoneX86_t& copy);
+
+		virtual ~DecodedInstructionCapstoneX86_t();
+
+		virtual string getDisassembly() const override;
+		virtual bool valid() const override;
+		virtual uint32_t length() const override;
+		virtual bool isBranch() const override;
+		virtual bool isCall() const override;
+		virtual bool isUnconditionalBranch() const override; 
+		virtual bool isConditionalBranch() const override; 
+		virtual bool isReturn() const override; 
+		virtual string getMnemonic() const override; 
+		virtual int64_t getImmediate() const override; 
+		virtual virtual_offset_t getAddress() const override; 
+		virtual bool setsStackPointer() const override; 
+		virtual uint32_t getPrefixCount() const override; 
+		virtual bool hasRelevantRepPrefix() const override; 
+		virtual bool hasRelevantRepnePrefix() const override; 
+		virtual bool hasRelevantOperandSizePrefix() const override; 
+		virtual bool hasRexWPrefix() const override; 
+		virtual bool hasImplicitlyModifiedRegs() const override;
+ 		virtual IRDB_SDK::VirtualOffset_t getMemoryDisplacementOffset(const DecodedOperand_t* t, const IRDB_SDK::Instruction_t* insn) const override;
+
+		// 0-based.  first operand is numbered 0.
+		virtual bool hasOperand(const int op_num) const override;
+		virtual std::shared_ptr<DecodedOperand_t> getOperand(const int op_num) const override;
+		virtual DecodedOperandVector_t getOperands() const override;
+
+	private:
+
+		void Disassemble(const virtual_offset_t start_addr, const void *data, const uint32_t max_len);
+
+		shared_ptr<void> my_insn;
+
+		class CapstoneHandle_t
+		{
+			public:
+				CapstoneHandle_t(FileIR_t* firp=NULL);
+				inline unsigned long getHandle() { return handle; }
+
+			private:
+				// csh handle; // this is the real type, but it's an alias and I don't want to export capstone values.
+				unsigned long handle;
+		};
+		static CapstoneHandle_t *cs_handle;
+
+
+		friend class DecodedInstruction_t;
+		friend class DecodedOperandCapstoneX86_t;
+
+		DecodedInstructionCapstoneX86_t(const shared_ptr<void> &my_insn);
+		DecodedInstructionCapstoneX86_t(const Instruction_t*);
+		DecodedInstructionCapstoneX86_t(const virtual_offset_t start_addr, const void *data, uint32_t max_len);
+		DecodedInstructionCapstoneX86_t(const virtual_offset_t start_addr, const void *data, const void* endptr);
+		DecodedInstructionCapstoneX86_t(const DecodedInstructionCapstoneX86_t& copy);
+};
+
+}
+
diff --git a/irdb-lib/libIRDB-core/include/decode_dispatch.hpp b/irdb-lib/libIRDB-core/include/decode_dispatch.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..491df5ca2ce2ff7daff7069a1a62cd23dee4f339
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/decode_dispatch.hpp
@@ -0,0 +1,55 @@
+
+namespace libIRDB
+{
+
+using namespace libIRDB;
+using namespace std;
+
+class DecodedOperandDispatcher_t;
+typedef std::vector<DecodedOperandDispatcher_t> DecodedOperandMetaVector_t;
+
+class DecodedInstructionDispatcher_t : virtual public IRDB_SDK::DecodedInstruction_t
+{
+	public:
+		DecodedInstructionDispatcher_t()=delete;
+		DecodedInstructionDispatcher_t(const Instruction_t*);
+		DecodedInstructionDispatcher_t(const virtual_offset_t start_addr, const void *data, uint32_t max_len);
+		DecodedInstructionDispatcher_t(const virtual_offset_t start_addr, const void *data, const void* endptr);
+		DecodedInstructionDispatcher_t(const DecodedInstructionDispatcher_t& copy);
+		DecodedInstructionDispatcher_t& operator=(const DecodedInstructionDispatcher_t& copy);
+
+		virtual ~DecodedInstructionDispatcher_t();
+
+		string getDisassembly() const;
+		bool valid() const;
+		uint32_t length() const;
+		bool isBranch() const;
+		bool isCall() const;
+		bool isUnconditionalBranch() const;
+		bool isConditionalBranch() const;
+		bool isReturn() const;
+		string getMnemonic() const;
+		int64_t getImmediate() const;
+		virtual_offset_t getAddress() const;
+		bool setsStackPointer() const;
+		uint32_t getPrefixCount() const;
+		bool hasRelevantRepPrefix() const;
+		bool hasRelevantRepnePrefix() const;
+		bool hasRelevantOperandSizePrefix() const;
+		bool hasRexWPrefix() const;
+		bool hasImplicitlyModifiedRegs() const;
+		IRDB_SDK::VirtualOffset_t getMemoryDisplacementOffset(const IRDB_SDK::DecodedOperand_t* t, const IRDB_SDK::Instruction_t* insn) const;
+
+		// 0-based.  first operand is numbered 0.
+		bool hasOperand(const int op_num) const;
+		shared_ptr<IRDB_SDK::DecodedOperand_t> getOperand(const int op_num) const;
+		IRDB_SDK::DecodedOperandVector_t getOperands() const;
+
+	private:
+
+		std::shared_ptr<DecodedInstructionCapstone_t> cs;
+
+};
+
+}
+
diff --git a/irdb-lib/libIRDB-core/include/doip.hpp b/irdb-lib/libIRDB-core/include/doip.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..e379150cd7f9e00507714c5bab40f4166bf2a36b
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/doip.hpp
@@ -0,0 +1,40 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+
+// The Digital Object Identifier for Peasoup.
+class doip_t : virtual public IRDB_SDK::Doip_t 
+{
+	public: 
+        	virtual ~doip_t(){}
+        	doip_t(db_id_t did, int conf, std::string tool_name , std::string comment);
+
+		db_id_t GetBaseID() const { return did; }
+   
+    private:
+        db_id_t did;
+        int confidence;
+        std::string tool_name;
+        std::string comment;
+};
+}
diff --git a/irdb-lib/libIRDB-core/include/eh.hpp b/irdb-lib/libIRDB-core/include/eh.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..77082ae522f1dcafd68ba4080ec539266f9f1f17
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/eh.hpp
@@ -0,0 +1,145 @@
+/*
+ * Copyright (c) 2017 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+using EhProgramInstruction_t = IRDB_SDK::EhProgramInstruction_t;
+using EhProgramListing_t     = IRDB_SDK::EhProgramListing_t;
+using EhProgramSet_t         = IRDB_SDK::EhProgramSet_t;
+using TTOrderVector_t        = IRDB_SDK::TTOrderVector_t;
+using EhCallSiteSet_t        = IRDB_SDK::EhCallSiteSet_t;
+
+class EhProgram_t : public BaseObj_t, virtual public IRDB_SDK::EhProgram_t
+{
+	public:
+
+	virtual ~EhProgram_t(){}
+	EhProgram_t(const EhProgram_t& orig)
+		: 
+		BaseObj_t(NULL)
+	{
+		cie_program=orig.cie_program;
+		fde_program=orig.fde_program;
+		code_alignment_factor=orig.code_alignment_factor;
+		data_alignment_factor=orig.data_alignment_factor;
+		return_register=orig.return_register;
+		ptrsize=orig.ptrsize;
+		setBaseID(BaseObj_t::NOT_IN_DATABASE);
+		GetRelocations()=orig.getRelocations();
+		
+	}
+	EhProgram_t(db_id_t id, const uint64_t caf, const int64_t daf, const uint8_t rr, const uint8_t p_ptrsize,
+			const EhProgramListing_t& ciep, const EhProgramListing_t& fdep)
+		: 
+		BaseObj_t(NULL), 
+		code_alignment_factor(caf), 
+		data_alignment_factor(daf), 
+		return_register(rr), 
+		ptrsize(p_ptrsize) ,
+		cie_program(ciep),
+		fde_program(fdep)
+	{ 
+		setBaseID(id); 
+	}
+
+
+	EhProgramListing_t& GetCIEProgram() { return cie_program; }
+	const EhProgramListing_t& getCIEProgram() const { return cie_program; }
+
+	EhProgramListing_t& GetFDEProgram() { return fde_program; }
+	const EhProgramListing_t& getFDEProgram() const { return fde_program; }
+	void setCIEProgram(const EhProgramListing_t& p) { cie_program=p; }
+	void setFDEProgram(const EhProgramListing_t& p) { fde_program=p; }
+
+
+        uint64_t getCodeAlignmentFactor() const { return code_alignment_factor; }
+        void setCodeAlignmentFactor(const uint64_t caf) 
+	{ 	
+		if ( ((uint8_t)caf) != caf  ) throw std::logic_error(std::string()+"Invalid code alignment factor in call to "+__FUNCTION__);
+		code_alignment_factor=(uint8_t)caf; 
+	}
+
+        int64_t getDataAlignmentFactor() const { return data_alignment_factor; }
+        void setDataAlignmentFactor(const int64_t daf) 
+	{ 
+		if ( (( int8_t)daf) != daf  ) throw std::logic_error(std::string()+"Invalid datat alignment factor in call to "+__FUNCTION__);
+		data_alignment_factor=(int8_t)daf; 
+	}
+
+        int64_t getReturnRegNumber() const { return return_register; }
+        void setReturnRegNumber(const uint8_t rr) { return_register=rr; }
+
+        std::vector<std::string> WriteToDB(File_t* fid);    // writes to DB, ID is not -1.
+
+        uint8_t getPointerSize() const { return ptrsize; }
+
+
+	friend bool operator<(const EhProgram_t&a, const EhProgram_t&b);
+
+	void print() const;
+
+	private:
+
+        uint8_t code_alignment_factor;
+        int8_t data_alignment_factor;
+        int8_t return_register;
+	uint8_t ptrsize; // needed for interpreting programs
+	EhProgramListing_t cie_program;
+	EhProgramListing_t fde_program;
+
+};
+bool operator<(const EhProgram_t&a, const EhProgram_t&b);
+
+
+class EhCallSite_t : public BaseObj_t, virtual public IRDB_SDK::EhCallSite_t
+{
+	public:
+
+	virtual ~EhCallSite_t(){}
+	EhCallSite_t(const db_id_t id, const uint64_t enc=0, IRDB_SDK::Instruction_t* lp=NULL) : 
+		BaseObj_t(NULL), 
+		tt_encoding(enc), 
+		landing_pad(lp)
+	{ setBaseID(id); }
+
+	uint64_t getTTEncoding() const { return tt_encoding; }
+	void setTTEncoding(const uint64_t p_tt) { tt_encoding=p_tt; }
+
+	IRDB_SDK::Instruction_t* getLandingPad() const { return landing_pad; }
+	void setLandingPad(IRDB_SDK::Instruction_t* lp) { landing_pad=dynamic_cast<Instruction_t*>(lp); if(lp) assert(landing_pad);  }
+
+	bool getHasCleanup() const ;
+	void setHasCleanup(bool p_has_cleanup=true) ;
+
+	TTOrderVector_t& GetTTOrderVector() { return ttov; }
+	const TTOrderVector_t& getTTOrderVector() const { return ttov; }
+	void setTTOrderVector(const TTOrderVector_t& p_ttov) { ttov=p_ttov; }
+
+        std::string WriteToDB(File_t* fid);    // writes to DB, ID is not -1.
+
+
+	private:
+
+	uint64_t tt_encoding;
+	IRDB_SDK::Instruction_t* landing_pad;
+	TTOrderVector_t ttov;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/file.hpp b/irdb-lib/libIRDB-core/include/file.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..da3db353a3bdd86e4a1d49ca3da90c1ed38fd2ca
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/file.hpp
@@ -0,0 +1,89 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+// An ELF file as represented by the DB
+class File_t : public BaseObj_t, virtual public IRDB_SDK::File_t
+{
+    public:
+        virtual ~File_t(){}
+        // create new item.
+        File_t( const db_id_t &file_id, const db_id_t &orig_fid, const std::string &url, 
+		const std::string &hash, const std::string &arch, const int &elfoid, 
+		const std::string &atn, const std::string &ftn, const std::string &itn, 
+		const std::string &icfs, const std::string &icfs_map, 
+		const std::string &rtn, const std::string &typ, const std::string &scoop, 
+		const std::string &ehpgms, const std::string &ehcss, 
+		const db_id_t &doipid);
+
+        File_t(db_id_t file_id) : BaseObj_t(NULL) { (void)file_id; assert(0);}          // read from DB       
+        void WriteToDB() { assert(0); }   // writes to DB ID is not -1.
+
+        std::string getAddressTableName() const { return address_table_name; }
+        std::string getFunctionTableName() const { return function_table_name; }
+        std::string getInstructionTableName() const { return instruction_table_name; }
+        std::string getICFSTableName() const { return icfs_table_name; }
+        std::string getICFSMapTableName() const { return icfs_map_table_name; }
+        std::string getRelocationsTableName() const { return relocs_table_name; }
+        std::string getTypesTableName() const { return types_table_name; }
+        std::string getScoopTableName() const { return scoop_table_name; }
+        std::string getEhProgramTableName() const { return ehpgm_table_name; }
+        std::string getEhCallSiteTableName() const { return ehcss_table_name; }
+        std::string getURL() const { return url; }
+
+	void CreateTables();
+
+	int getELFOID() const { return elfoid; };
+	db_id_t getFileID() const {return orig_fid; };
+
+        friend class FileIR_t;
+        friend class Function_t;
+        friend class AddressID_t;
+        friend class Instruction_t;
+        friend class VariantID_t;
+        friend class Relocation_t;
+        friend class Type_t;
+        friend class BasicType_t;
+        friend class PointerType_t;
+        friend class AggregateType_t;
+        friend class FuncType_t;
+        friend class ICFS_t;
+	friend class DataScoop_t;
+//        friend class IBTargets;
+
+    private:
+	db_id_t orig_fid;
+        std::string url;
+        std::string hash;
+        std::string arch;       
+        std::string address_table_name;
+        std::string function_table_name;
+        std::string instruction_table_name;
+        std::string icfs_table_name;
+        std::string icfs_map_table_name;
+        std::string relocs_table_name;
+        std::string types_table_name;
+        std::string scoop_table_name;
+        std::string ehpgm_table_name;
+        std::string ehcss_table_name;
+	int elfoid;
+};
+}
diff --git a/irdb-lib/libIRDB-core/include/fileir.hpp b/irdb-lib/libIRDB-core/include/fileir.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..17b9a9c5fb4d0c753cbbcd1881ac26da57fd8e02
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/fileir.hpp
@@ -0,0 +1,235 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+using namespace std;
+using FunctionSet_t = IRDB_SDK::FunctionSet_t;
+using AddressSet_t  = IRDB_SDK::AddressSet_t ;
+
+// A variant of a problem, this
+// may be an original variant
+// (i.e., and unmodified Variant) or a modified variant.
+class FileIR_t : public BaseObj_t, virtual public IRDB_SDK::FileIR_t
+{
+	public:
+
+		// Create a Variant from the database
+		FileIR_t(const VariantID_t &newprogid, File_t* fid=NULL);
+		virtual ~FileIR_t();
+	  
+		// DB operations
+		void writeToDB(std::ostream *verbose_logging=&std::cerr);
+
+		// accessors and mutators in one
+		FunctionSet_t&          GetFunctions()       { return funcs; }
+		const FunctionSet_t&    getFunctions() const { return funcs; }
+
+		InstructionSet_t&       GetInstructions()       { return insns; }
+		const InstructionSet_t& getInstructions() const { return insns; }
+
+		AddressSet_t&           GetAddresses()       { return addrs; }
+		const AddressSet_t&     getAddresses() const { return addrs; }
+
+		RelocationSet_t&        GetRelocations()       { return relocs; }
+		const RelocationSet_t&  getRelocations() const { return relocs; }
+
+		DataScoopSet_t&         GetDataScoops()       { return scoops; }
+		const DataScoopSet_t&   getDataScoops() const { return scoops; }
+
+		ICFSSet_t&              GetAllICFS()       { return icfs_set; }
+		const ICFSSet_t&        getAllICFS() const { return icfs_set; }
+
+		EhProgramSet_t&         GetAllEhPrograms()       { return eh_pgms; }
+		const EhProgramSet_t&   getAllEhPrograms() const { return eh_pgms; }
+
+		EhCallSiteSet_t&        GetAllEhCallSites()       { return eh_css; }
+		const EhCallSiteSet_t&  getAllEhCallSites() const { return eh_css; }
+
+		// generate the spri rules into the output file, fout.
+		void GenerateSPRI(std::ostream &fout, bool with_ilr=false);
+
+		// generate spri, assume that orig_varirp is the original variant. 
+		void GenerateSPRI(FileIR_t *orig_varirp, std::ostream &fout, bool with_ilr=false);
+
+		void setBaseIDS();
+		IRDB_SDK::DatabaseID_t getMaxBaseID() const;
+
+		File_t* getFile() const { return fileptr; }
+
+		// Used for modifying a large number of instructions. AssembleRegistry
+		// assembles the assembly isntructions for each registered instruction
+		// and clears the registry. RegisterAssembly registers the instruction
+		// to be assembled later. 
+		void assembleRegistry();
+		void registerAssembly(IRDB_SDK::Instruction_t *instr, string assembly);
+		void unregisterAssembly(IRDB_SDK::Instruction_t *instr);
+		string lookupAssembly(IRDB_SDK::Instruction_t *instr);
+
+		//Needed for inserting assembly before an instruction. 
+		//if orig is not registered, the function returns, otherwise
+		//the instruction/assembly mapping of orig->assembly is altered to
+		//updated->assembly
+		//removes the mapping for orig->assembly from the map. 
+		void changeRegistryKey(IRDB_SDK::Instruction_t* orig,  IRDB_SDK::Instruction_t* updated);
+
+		void setArchitecture();
+
+		static void setArchitecture(const int width, const  IRDB_SDK::ADMachineType_t mt);
+		// static const  IRDB_SDK::ArchitectureDescription_t* getArchitecture() { return archdesc; }
+
+		// Lookup a scoop by address
+		IRDB_SDK::DataScoop_t* findScoop(const IRDB_SDK::VirtualOffset_t &addr) const;
+
+		void splitScoop(IRDB_SDK::DataScoop_t *tosplit, const IRDB_SDK::VirtualOffset_t &addr, size_t size, 
+				IRDB_SDK::DataScoop_t* &before, IRDB_SDK::DataScoop_t* &containing,  IRDB_SDK::DataScoop_t* &after, IRDB_SDK::DatabaseID_t *max_id=NULL);
+
+		virtual IRDB_SDK::EhCallSite_t* addEhCallSite_t(IRDB_SDK::Instruction_t* for_insn, const uint64_t enc=0, IRDB_SDK::Instruction_t* lp=nullptr) ;
+
+		virtual IRDB_SDK::Relocation_t* addNewRelocation(
+                        IRDB_SDK::BaseObj_t* from_obj,
+                        int32_t _offset,
+                        string _type,
+                        IRDB_SDK::BaseObj_t* p_wrt_obj=nullptr,
+                        int32_t p_addend=0) ;
+		virtual EhProgram_t* addEhProgram(
+		        IRDB_SDK::Instruction_t* insn=nullptr,
+			const uint64_t caf=1,
+			const int64_t daf=1,
+			const uint8_t rr=1,
+			const uint8_t p_ptrsize=8,
+			const EhProgramListing_t& p_cie_program={},
+			const EhProgramListing_t& p_fde_program={}
+			) ;
+		virtual IRDB_SDK::AddressID_t* addNewAddress(const IRDB_SDK::DatabaseID_t& myfileID, const IRDB_SDK::VirtualOffset_t& voff=0) ;
+		virtual IRDB_SDK::ICFS_t*      addNewICFS   (
+			IRDB_SDK::Instruction_t* insn=nullptr, 
+			const IRDB_SDK::InstructionSet_t& targets={}, 
+			const IRDB_SDK::ICFSAnalysisStatus_t& status=IRDB_SDK::iasAnalysisIncomplete);
+		virtual IRDB_SDK::Instruction_t* addNewInstruction(
+			IRDB_SDK::AddressID_t* addr=nullptr, 
+			IRDB_SDK::Function_t* func=nullptr, 
+			const string& bits="", 
+			const string& comment="user-added", 
+			IRDB_SDK::AddressID_t* indTarg=nullptr);
+
+			virtual IRDB_SDK::DataScoop_t* addNewDataScoop(
+				const string& p_name="user-added",
+				IRDB_SDK::AddressID_t* p_start=nullptr,
+				IRDB_SDK::AddressID_t* p_end=nullptr,
+				IRDB_SDK::Type_t* p_type=nullptr,
+				uint8_t p_permissions=0,
+				bool p_is_relro=false,
+				const string &p_contents="",
+				IRDB_SDK::DatabaseID_t id=BaseObj_t::NOT_IN_DATABASE);
+
+		virtual void removeScoop(IRDB_SDK::DataScoop_t* s) ;
+		virtual void moveRelocation(IRDB_SDK::Relocation_t* reloc, IRDB_SDK::Instruction_t* from, IRDB_SDK::Instruction_t* to) ;
+		virtual IRDB_SDK::EhProgram_t* copyEhProgram(const IRDB_SDK::EhProgram_t& orig);
+
+		virtual void   setAllEhPrograms(const EhProgramSet_t& new_pgms)  { eh_pgms=new_pgms; }
+
+
+
+
+
+
+
+	private:
+
+		static ArchitectureDescription_t *archdesc;
+
+		#define ASM_REG_MAX_SIZE 500000
+
+		typedef std::map<Instruction_t*,string> registry_type;
+
+		// a pointer to the original variants IR, NULL means not yet loaded.
+		FileIR_t* orig_variant_ir_p;
+
+		registry_type assembly_registry;
+
+		void ReadFromDB();	//accesses DB
+
+		FunctionSet_t     funcs;
+		InstructionSet_t  insns;
+		AddressSet_t      addrs;
+		RelocationSet_t   relocs;
+		TypeSet_t         types;
+		DataScoopSet_t    scoops;
+	        VariantID_t&      progid;    // Not owned by fileIR
+		ICFSSet_t         icfs_set;
+		File_t*           fileptr;   // Owned by variant, not fileIR
+		EhProgramSet_t    eh_pgms;
+		EhCallSiteSet_t   eh_css;
+
+		map<db_id_t,AddressID_t*> ReadAddrsFromDB();
+		map<db_id_t,EhProgram_t*> ReadEhPgmsFromDB();
+		
+		map<db_id_t,EhCallSite_t*> ReadEhCallSitesFromDB
+		(
+			map<EhCallSite_t*,db_id_t> &unresolvedEhCssLandingPads
+		);
+
+		map<db_id_t,Function_t*> ReadFuncsFromDB
+		(
+			map<db_id_t,AddressID_t*> &addrMap,
+			map<db_id_t,Type_t*> &typeMap,
+			map<Function_t*,db_id_t> &entry_points
+		);
+
+		map<db_id_t,DataScoop_t*> ReadScoopsFromDB
+		(
+			map<db_id_t,AddressID_t*> &addrMap,
+			map<db_id_t,Type_t*> &typeMap
+		);
+
+		map<db_id_t,Instruction_t*> ReadInsnsFromDB 
+		(	
+			const map<db_id_t,Function_t*> &funcMap,
+			const map<db_id_t,AddressID_t*> &addrMap,
+			const map<db_id_t,EhProgram_t*> &ehpgmMap,
+			const map<db_id_t,EhCallSite_t*> &ehcsMap,
+			map<db_id_t,Instruction_t*> &addressToInstructionMap,
+			map<Instruction_t*, db_id_t> &unresolvedICFS
+		);
+
+		void ReadRelocsFromDB
+		(
+			map<db_id_t,BaseObj_t*>		&insnMap
+		);
+
+		map<db_id_t, Type_t*> ReadTypesFromDB(TypeSet_t& types);
+		void ReadAllICFSFromDB(map<db_id_t,Instruction_t*> &addr2insnMap,
+			map<Instruction_t*, db_id_t> &unresolvedICFS);
+
+		void CleanupICFS(ostream *verbose_logging=&cerr);
+		void GarbageCollectICFS(ostream *verbose_logging=&cerr);
+		void DedupICFS(ostream *verbose_logging=&cerr);
+
+
+		clock_t ReadIRDB_start;
+		clock_t ReadIRDB_end;
+
+		friend IRDB_SDK::FileIR_t;
+
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/function.hpp b/irdb-lib/libIRDB-core/include/function.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..50731fd873e70a9d116a535d0d108ec92299155a
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/function.hpp
@@ -0,0 +1,72 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+// The basic Function of a variant.
+class Function_t : public BaseObj_t, virtual public IRDB_SDK::Function_t
+{
+    public:
+	
+	virtual ~Function_t() {}
+	Function_t() : BaseObj_t(NULL) {}	// create a new function not in the db 
+
+	// create a function that's already in the DB  
+	Function_t(db_id_t id, std::string name, int size, int oa_size, bool use_fp, bool is_safe, IRDB_SDK::FuncType_t *, IRDB_SDK::Instruction_t *entry);	
+
+	InstructionSet_t& GetInstructions() { return my_insns; }
+	const InstructionSet_t& getInstructions() const { return my_insns; }
+
+        const int getStackFrameSize() const { return stack_frame_size; }
+        const std::string& getName() const { return name; }
+        uint32_t getOutArgsRegionSize() const { return out_args_region_size; }
+
+        void setStackFrameSize(int size) { stack_frame_size=size; }
+        void setName(std::string newname)	 { name=newname; }
+        void setOutArgsRegionSize(uint32_t oa_size) {out_args_region_size=oa_size;}
+
+	void setEntryPoint(IRDB_SDK::Instruction_t *insn) { entry_point=dynamic_cast<Instruction_t*>(insn); if(insn) assert(entry_point);  }
+	IRDB_SDK::Instruction_t* getEntryPoint() const { return entry_point;}
+
+	std::string WriteToDB(File_t *fid, db_id_t newid);
+
+        bool getUseFramePointer() const { return use_fp; }
+        void setUseFramePointer(bool useFP) { use_fp = useFP; }
+
+        void setSafe(bool safe) { is_safe = safe; }
+        bool isSafe() const { return is_safe; }
+
+	void setType(IRDB_SDK::FuncType_t *t) ; // { function_type = dynamic_cast<FuncType_t*>(t); if(t) assert(function_type); }
+	IRDB_SDK::FuncType_t* getType() const ; // { return function_type; }
+
+	int getNumArguments() const;
+
+    private:
+	Instruction_t *entry_point;
+	InstructionSet_t my_insns;
+        int stack_frame_size;
+        std::string name;
+        uint32_t out_args_region_size;
+        bool use_fp;
+        bool is_safe;
+	FuncType_t *function_type;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/icfs.hpp b/irdb-lib/libIRDB-core/include/icfs.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..c18efe782582386561d1a9b17df9156599367773
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/icfs.hpp
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+using InstructionSet_t       = IRDB_SDK::InstructionSet_t;
+using ICFS_Analysis_Status_t = IRDB_SDK::ICFSAnalysisStatus_t;
+using ICFSSet_t              = IRDB_SDK::ICFSSet_t;
+
+// these must match the allowed values for type icfs_analysis_result in Postgres DB
+#define ICFS_ANALYSIS_INCOMPLETE_STR "icfs_analysis_incomplete"
+#define ICFS_ANALYSIS_MODULE_COMPLETE_STR "icfs_analysis_module_complete"
+#define ICFS_ANALYSIS_COMPLETE_STR "icfs_analysis_complete"
+
+// Keep track of instruction control flow sets
+class ICFS_t : virtual public InstructionSet_t, public BaseObj_t, virtual public IRDB_SDK::ICFS_t
+{
+	public:
+		virtual ~ICFS_t(){}
+		ICFS_t(): BaseObj_t(NULL), m_icfs_analysis_status(IRDB_SDK::iasAnalysisIncomplete) {}
+		ICFS_t(const ICFS_Analysis_Status_t p_status) : BaseObj_t(NULL), m_icfs_analysis_status(p_status) {}
+		ICFS_t(db_id_t p_set_id, const ICFS_Analysis_Status_t p_status = IRDB_SDK::iasAnalysisIncomplete);
+		ICFS_t(db_id_t p_set_id, const std::string);
+		std::string WriteToDB(File_t *fid);
+		 
+
+		// this is bad -- you loose data with this operator=.
+
+		void setTargets(const InstructionSet_t &other) 
+		{
+			InstructionSet_t::operator=(other);
+		}
+		void addTargets(const InstructionSet_t &other) 
+		{
+			insert(std::begin(other), std::end(other)); 
+		}
+
+		bool isIncomplete() const {
+			return getAnalysisStatus() == IRDB_SDK::iasAnalysisIncomplete;
+		}
+
+		bool isComplete() const {
+			return getAnalysisStatus() == IRDB_SDK::iasAnalysisComplete;
+		}
+
+		bool isModuleComplete() const {
+			return getAnalysisStatus() == IRDB_SDK::iasAnalysisModuleComplete;
+		}
+
+		void setAnalysisStatus(const ICFS_Analysis_Status_t p_status) {
+			m_icfs_analysis_status = p_status;
+		}
+
+		ICFS_Analysis_Status_t getAnalysisStatus() const { 
+			return m_icfs_analysis_status;
+		}
+
+	private:
+		ICFS_Analysis_Status_t m_icfs_analysis_status;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/instruction.hpp b/irdb-lib/libIRDB-core/include/instruction.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..0a332983d156da80f52f9f2774dfe4a57a0a0b0b
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/instruction.hpp
@@ -0,0 +1,91 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+using RelocationSet_t = IRDB_SDK::RelocationSet_t; 
+
+// The basic instruction of a variant.
+class Instruction_t : public BaseObj_t, virtual public IRDB_SDK::Instruction_t
+{
+	public:
+		virtual ~Instruction_t(){}
+		Instruction_t();
+		Instruction_t(db_id_t id, AddressID_t *addr, Function_t *func, db_id_t orig_id, 
+		std::string data, std::string callback, std::string comment, AddressID_t *my_indTarg, db_id_t doip_id);
+
+		IRDB_SDK::AddressID_t* getAddress() const  { return my_address; } 
+		IRDB_SDK::Function_t* getFunction() const ; // { return my_function; } 
+		db_id_t getOriginalAddressID() const { return orig_address_id; } 
+		IRDB_SDK::Instruction_t* getFallthrough() const { return fallthrough; } 
+		IRDB_SDK::Instruction_t* getTarget() const { return target; } 
+		IRDB_SDK::ICFS_t* getIBTargets() const  { return icfs; }
+
+		std::string getDataBits()  const { return data; } 
+		std::string getCallback()  const { return callback; } 
+		std::string getComment()   const { return comment; } 
+		IRDB_SDK::EhProgram_t* getEhProgram() const ; // { return eh_pgm; }
+		IRDB_SDK::EhCallSite_t* getEhCallSite() const ; // { return eh_cs; }
+
+  
+		void setAddress(IRDB_SDK::AddressID_t* newaddr)  ; // { my_address=newaddr; }
+		void setFunction(IRDB_SDK::Function_t* func   )  ; // { my_function=func;}
+		void setOriginalAddressID(db_id_t origid) { orig_address_id=origid; /* you shouldn't do this, unless you know what you're doing! */}
+		void setFallthrough(IRDB_SDK::Instruction_t* i) ; // { fallthrough=i; }
+		void setTarget(IRDB_SDK::Instruction_t* i)	  ; // { target=i; }
+		void setIBTargets(IRDB_SDK::ICFS_t *p_icfs)	 ; // { icfs=p_icfs; }
+		void setDataBits(std::string orig)	{ data=orig; }
+		void setCallback(std::string orig)	{ callback=orig; }
+		void setComment(std::string orig)	 { comment=orig; }
+		void setEhProgram(IRDB_SDK::EhProgram_t* orig)	 ; // { eh_pgm=orig; }
+		void setEhCallSite(IRDB_SDK::EhCallSite_t* orig); // 	 { eh_cs=orig; }
+
+		IRDB_SDK::AddressID_t* getIndirectBranchTargetAddress() const; // { return indTarg; }
+		void setIndirectBranchTargetAddress(IRDB_SDK::AddressID_t* myIndTarg) ; // { indTarg=myIndTarg; }
+
+		void WriteToDB() { assert(0); }
+		std::vector<std::string> WriteToDB(File_t *fid, db_id_t newid); 
+		// int Disassemble(DISASM &d) const; 
+		std::string getDisassembly() const;
+		bool assemble(std::string assembly);
+
+		bool isFunctionExit() const;
+
+		//static bool SetsStackPointer(DISASM *disasm);
+		//static bool SetsStackPointer(ARGTYPE* arg);
+
+		bool IsSyscall() { return getDisassembly().find("int 0x80") != std::string::npos; }
+
+	private:
+		AddressID_t*	my_address;
+		Function_t*	 my_function;
+		db_id_t		 orig_address_id;		// const, should not change.
+		Instruction_t*  fallthrough;
+		Instruction_t*  target;
+		std::string	 data;
+		std::string	 callback;	// name of callback handler (if any)
+		std::string	 comment;
+		AddressID_t*	indTarg;
+		ICFS_t*		 icfs;
+		EhProgram_t*	 eh_pgm;
+		EhCallSite_t*	 eh_cs;
+};
+}
diff --git a/irdb-lib/libIRDB-core/include/libIRDB-core.hpp b/irdb-lib/libIRDB-core/include/libIRDB-core.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..681d93a330914a1953761dee21fb246b913d08b4
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/libIRDB-core.hpp
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef libIRDB_core
+#define libIRDB_core
+
+#include <string>
+#include <vector>
+#include <set>
+#include <assert.h>
+#include <string.h>
+#include <iostream>
+#include <pqxx/pqxx>
+#include <ctime>
+#include <stdint.h>
+
+// include SDK
+#include <irdb-core>
+
+#include <basetypes.hpp>
+#include <dbinterface.hpp>
+#include <doip.hpp>
+#include <baseobj.hpp>
+#include <reloc.hpp>
+#include <address.hpp>
+#include <icfs.hpp>
+#include <instruction.hpp>
+#include <file.hpp>
+#include <function.hpp>
+#include <variantid.hpp>
+#include <archdesc.hpp>
+#include <type.hpp>
+#include <scoop.hpp>
+#include <eh.hpp>
+#include <fileir.hpp>
+#include <pqxxdb.hpp>
+#include <IRDB_Objects.hpp>
+#include <transform_step.h>
+#include <decode.hpp>
+
+int command_to_stream(const std::string& command, std::ostream& stream);
+
+
+#endif
diff --git a/irdb-lib/libIRDB-core/include/operand_base.hpp b/irdb-lib/libIRDB-core/include/operand_base.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..7c408fc3f96a55cac0e295a15a6ecbe4a564fa57
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/operand_base.hpp
@@ -0,0 +1,45 @@
+#if 0
+namespace libIRDB
+{
+
+using namespace std;
+using namespace libIRDB;
+
+
+class DecodedOperandCapstone_t : virtual public IRDB_SDK::DecodedOperand_t 
+{
+	public:
+		virtual bool isConstant() const=0;
+		virtual uint64_t getConstant() const=0;
+		virtual string getString() const=0;
+		virtual bool isRegister() const=0;
+		virtual bool isGeneralPurposeRegister() const=0;
+		virtual bool isMmxRegister() const=0;
+		virtual bool isFpuRegister() const=0;
+		virtual bool isSseRegister() const=0;
+		virtual bool isAvxRegister() const=0;
+		virtual bool isZmmRegister() const=0;
+		virtual bool isSpecialRegister() const=0;
+		virtual bool isSegmentRegister() const=0;
+		virtual uint32_t getRegNumber() const=0;
+		virtual bool isMemory() const=0;
+		virtual bool hasSegmentRegister() const=0;
+		virtual uint32_t getSegmentRegister() const=0;
+		virtual bool hasBaseRegister() const=0;
+		virtual bool hasIndexRegister() const=0;
+		virtual uint32_t getBaseRegister() const=0;
+		virtual uint32_t getIndexRegister() const=0;
+		virtual bool hasMemoryDisplacement() const=0;
+		virtual virtual_offset_t getMemoryDisplacement() const=0;
+		virtual bool isPcrel() const=0;
+		virtual uint32_t getScaleValue() const=0;
+		virtual uint32_t getMemoryDisplacementEncodingSize() const=0;
+		virtual uint32_t getArgumentSizeInBytes() const=0;
+		virtual uint32_t getArgumentSizeInBits() const=0;
+		virtual bool isRead() const=0; 
+		virtual bool isWritten() const=0; 
+
+};
+
+}
+#endif
diff --git a/irdb-lib/libIRDB-core/include/operand_csarm.hpp b/irdb-lib/libIRDB-core/include/operand_csarm.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..da26a2105ca45719f9262f9e0a9912939195e7fa
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/operand_csarm.hpp
@@ -0,0 +1,57 @@
+
+namespace libIRDB
+{
+
+using namespace std;
+using namespace libIRDB;
+
+class DecodedOperandCapstoneARM64_t;
+
+class DecodedOperandCapstoneARM64_t : virtual public IRDB_SDK::DecodedOperand_t
+{
+	public:
+		DecodedOperandCapstoneARM64_t() =delete;
+		virtual ~DecodedOperandCapstoneARM64_t();
+
+		virtual bool isConstant() const override;
+		virtual uint64_t getConstant() const override;
+		virtual string getString() const override;
+		virtual bool isRegister() const override;
+		virtual bool isGeneralPurposeRegister() const override;
+		virtual bool isMmxRegister() const override;
+		virtual bool isFpuRegister() const override;
+		virtual bool isSseRegister() const override;
+		virtual bool isAvxRegister() const override;
+		virtual bool isZmmRegister() const override;
+		virtual bool isSpecialRegister() const override;
+		virtual bool isSegmentRegister() const override;
+		virtual uint32_t getRegNumber() const override;
+		virtual bool isMemory() const override;
+		virtual bool hasSegmentRegister() const override;
+		virtual uint32_t getSegmentRegister() const override;
+		virtual bool hasBaseRegister() const override;
+		virtual bool hasIndexRegister() const override;
+		virtual uint32_t getBaseRegister() const override;
+		virtual uint32_t getIndexRegister() const override;
+		virtual bool hasMemoryDisplacement() const override;
+		virtual virtual_offset_t getMemoryDisplacement() const override;
+		virtual bool isPcrel() const override;
+		virtual uint32_t getScaleValue() const override;
+		virtual uint32_t getMemoryDisplacementEncodingSize() const override;
+		virtual uint32_t getArgumentSizeInBytes() const override;
+		virtual uint32_t getArgumentSizeInBits() const override;
+		virtual bool isRead() const override; 
+		virtual bool isWritten() const override; 
+
+
+	private:
+
+		DecodedOperandCapstoneARM64_t( const shared_ptr<void> &my_insn, uint8_t op_num);
+
+		shared_ptr<void> my_insn;
+		uint8_t op_num;
+
+		friend class DecodedInstructionCapstoneARM64_t;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/operand_csx86.hpp b/irdb-lib/libIRDB-core/include/operand_csx86.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..2c2a250824843b0c151162d2bb330d070143cf74
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/operand_csx86.hpp
@@ -0,0 +1,58 @@
+
+namespace libIRDB
+{
+
+using namespace std;
+using namespace libIRDB;
+
+class DecodedInstructionCapstoneX86_t;
+
+class DecodedOperandCapstoneX86_t : virtual public IRDB_SDK::DecodedOperand_t
+{
+	public:
+		DecodedOperandCapstoneX86_t() =delete;
+		virtual ~DecodedOperandCapstoneX86_t();
+
+		virtual bool isConstant() const override;
+		virtual uint64_t getConstant() const override;
+		virtual string getString() const override;
+		virtual bool isRegister() const override;
+		virtual bool isGeneralPurposeRegister() const override;
+		virtual bool isMmxRegister() const override;
+		virtual bool isFpuRegister() const override;
+		virtual bool isSseRegister() const override;
+		virtual bool isAvxRegister() const override;
+		virtual bool isZmmRegister() const override;
+		virtual bool isSpecialRegister() const override;
+		virtual bool isSegmentRegister() const override;
+		virtual uint32_t getRegNumber() const override;
+		virtual bool isMemory() const override;
+		virtual bool hasSegmentRegister() const override;
+		virtual uint32_t getSegmentRegister() const override;
+		virtual bool hasBaseRegister() const override;
+		virtual bool hasIndexRegister() const override;
+		virtual uint32_t getBaseRegister() const override;
+		virtual uint32_t getIndexRegister() const override;
+		virtual bool hasMemoryDisplacement() const override;
+		virtual virtual_offset_t getMemoryDisplacement() const override;
+		virtual bool isPcrel() const override;
+		virtual uint32_t getScaleValue() const override;
+		virtual uint32_t getMemoryDisplacementEncodingSize() const override;
+		virtual uint32_t getArgumentSizeInBytes() const override;
+		virtual uint32_t getArgumentSizeInBits() const override;
+		virtual bool isRead() const override; 
+		virtual bool isWritten() const override; 
+
+
+	private:
+
+		DecodedOperandCapstoneX86_t( const shared_ptr<void> &my_insn, uint8_t op_num);
+
+		shared_ptr<void> my_insn;
+		uint8_t op_num;
+
+		friend class DecodedInstructionCapstoneX86_t;
+
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/operand_dispatch.hpp b/irdb-lib/libIRDB-core/include/operand_dispatch.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..7d7087668047338a912eb5ea7239fd15dfb05d0c
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/operand_dispatch.hpp
@@ -0,0 +1,55 @@
+namespace libIRDB
+{
+
+using namespace std;
+using namespace libIRDB;
+
+
+class DecodedOperandDispatcher_t : virtual public IRDB_SDK::DecodedOperand_t
+{
+	public:
+		DecodedOperandDispatcher_t() =delete;
+		DecodedOperandDispatcher_t& operator=(const DecodedOperandDispatcher_t& copy);
+		DecodedOperandDispatcher_t(const DecodedOperandDispatcher_t& copy);
+		virtual ~DecodedOperandDispatcher_t();
+
+		bool isConstant() const;
+		uint64_t getConstant() const;
+		string getString() const;
+		bool isRegister() const;
+		bool isGeneralPurposeRegister() const;
+		bool isMmxRegister() const;
+		bool isFpuRegister() const;
+		bool isSseRegister() const;
+		bool isAvxRegister() const;
+		bool isSpecialRegister() const;
+		bool isSegmentRegister() const;
+		uint32_t getRegNumber() const;
+		bool isMemory() const;
+		bool hasSegmentRegister() const;
+		uint32_t getSegmentRegister() const;
+		bool hasBaseRegister() const;
+		bool hasIndexRegister() const;
+		uint32_t getBaseRegister() const;
+		uint32_t getIndexRegister() const;
+		bool hasMemoryDisplacement() const;
+		virtual_offset_t getMemoryDisplacement() const;
+		bool isPcrel() const;
+		uint32_t getScaleValue() const;
+		uint32_t getMemoryDisplacementEncodingSize() const;
+		uint32_t getArgumentSizeInBytes() const;
+		uint32_t getArgumentSizeInBits() const;
+		bool isRead() const; 
+		bool isWritten() const; 
+
+
+	private:
+		DecodedOperandDispatcher_t(const shared_ptr<DecodedOperandCapstone_t> in);
+
+		std::shared_ptr<DecodedOperandCapstone_t> cs;
+
+		friend class DecodedInstructionDispatcher_t;
+
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/pqxxdb.hpp b/irdb-lib/libIRDB-core/include/pqxxdb.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..031bd635313ae1a7e1c950ea74387cd9e4d6ebbb
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/pqxxdb.hpp
@@ -0,0 +1,50 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+
+class pqxxDB_t : public DBinterface_t, virtual public IRDB_SDK::pqxxDB_t
+{
+	public:
+		pqxxDB_t();
+		virtual ~pqxxDB_t() override
+        	{
+                    // do nothing
+        	};
+		void issueQuery(std::string query);
+		void issueQuery(std::stringstream & query);
+		void moveToNextRow();
+		std::string getResultColumn(std::string colname);
+		bool isDone();
+		void commit();
+
+		pqxx::connection& getConnection() { return conn; }
+		pqxx::work& getTransaction() { return txn; }
+
+	private:
+		pqxx::connection conn;
+		pqxx::work txn;
+		pqxx::result results;
+		pqxx::result::const_iterator results_iter;
+
+};
+}
diff --git a/irdb-lib/libIRDB-core/include/reloc.hpp b/irdb-lib/libIRDB-core/include/reloc.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..bcd911010fee1e4309eb273fd797966c8fd1a537
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/reloc.hpp
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+// An ELF file as represented by the DB
+class Relocation_t : public BaseObj_t, virtual public IRDB_SDK::Relocation_t
+{
+    public:
+
+        // create new item.
+        virtual ~Relocation_t() {}
+        Relocation_t() : BaseObj_t(NULL), offset(0), wrt_obj(NULL), addend(0)  {}	// new reloc w/no data
+
+	// a reloc read from the DB 
+        Relocation_t(db_id_t reloc_id, int _offset, std::string _type, IRDB_SDK::BaseObj_t* p_wrt_obj=NULL, int32_t p_addend=0) :
+		BaseObj_t(NULL), offset(_offset), type(_type), wrt_obj(p_wrt_obj), addend(p_addend) { setBaseID(reloc_id); }
+
+
+        void WriteToDB() { assert(0); }   // writes to DB ID is not -1.
+        std::vector<std::string> WriteToDB(File_t* fid, BaseObj_t* insn);    // writes to DB, ID is not -1.
+
+	void setOffset(int off) { offset=off;}
+	int getOffset() const { return offset; }
+	void setType(std::string ty) { type=ty;}
+	std::string getType() const { return type; }
+
+	void setAddend(uint32_t p_addend) { addend=p_addend;}
+	uint32_t getAddend() const { return addend; }
+
+	/* get and set "with respect to" field */
+	void setWRT(IRDB_SDK::BaseObj_t* WRT) { wrt_obj=dynamic_cast<BaseObj_t*>(WRT); if(WRT) assert(wrt_obj); }
+	IRDB_SDK::BaseObj_t* getWRT() const { return wrt_obj; }
+
+        friend class FileIR_t;
+        friend class Function_t;
+        friend class AddressID_t;
+        friend class Instruction_t;
+        friend class VariantID_t;
+
+    private:
+	int offset;		// how far into the instruction the relocation should be applied.
+	std::string type;	// a string that describes the relocation type.  
+				// possible values:  32-bit, pcrel
+
+	IRDB_SDK::BaseObj_t* wrt_obj;
+	int32_t addend;
+};
+}
diff --git a/irdb-lib/libIRDB-core/include/scoop.hpp b/irdb-lib/libIRDB-core/include/scoop.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..1985de0c01a347e195b36d605fc9dde0620e7045
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/scoop.hpp
@@ -0,0 +1,137 @@
+/*
+ * Copyright (c) 2016 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+namespace libIRDB
+{
+
+class DataScoopByAddressComp_t;
+
+class DataScoop_t : public BaseObj_t, virtual public IRDB_SDK::DataScoop_t
+{
+
+	public:
+		DataScoop_t()
+			:
+				BaseObj_t(NULL),
+				name(),
+				start(NULL),
+				end(NULL),
+				type(NULL),
+				permissions(0),
+				is_relro(false),
+				contents()
+		{}
+	
+		DataScoop_t( 	libIRDB::db_id_t id,
+				std::string p_name,
+				libIRDB::AddressID_t* p_start,
+				libIRDB::AddressID_t* p_end,
+				libIRDB::Type_t* p_type,
+				int p_permissions, 
+				bool p_is_relro, 
+				const std::string &p_contents)
+			:
+				BaseObj_t(NULL),
+				name(p_name),
+				start(p_start),
+				end(p_end),
+				type(p_type),
+				permissions(p_permissions),
+				is_relro(p_is_relro),
+				contents(p_contents)
+		{
+			assert(start && end);
+			setBaseID(id);
+		}
+
+		virtual ~DataScoop_t() { /* management of addresses and types is explicit */ } 
+
+		const std::string getName() const { return name; }
+		const std::string& getContents() const { return contents; }
+		std::string &getContents() { return contents; }
+		IRDB_SDK::AddressID_t* getStart() const { return start; }
+		IRDB_SDK::AddressID_t* getEnd() const { return end; }
+		IRDB_SDK::Type_t* getType() const { return type; }
+		IRDB_SDK::VirtualOffset_t getSize() const { assert(start && end); return end->getVirtualOffset() - start->getVirtualOffset() + 1 ; }
+		bool isReadable() const  { return (permissions & permissions_r) == permissions_r; }
+		bool isWriteable() const { return (permissions & permissions_w) == permissions_w; };
+		bool isExecuteable() const { return (permissions & permissions_x) == permissions_x; };
+		bool isRelRo() const { return is_relro; };
+		uint8_t  getRawPerms() const { return permissions; }
+		void  setRawPerms(int newperms) { permissions=newperms; }
+
+		void setName(const std::string &n) { name=n; }
+		void setContents(const std::string &n) { contents=n; }
+		void setStart( IRDB_SDK::AddressID_t* addr) { assert(addr); start=dynamic_cast<AddressID_t*>(addr); assert(start); }
+		void setEnd  ( IRDB_SDK::AddressID_t* addr) { assert(addr); end  =dynamic_cast<AddressID_t*>(addr); assert(end  ); }
+		void setType( IRDB_SDK::Type_t*  t) { type=dynamic_cast<Type_t*>(t); }
+
+		void setReadable() { permissions |= permissions_r; }
+		void setWriteable() { permissions |= permissions_w; }
+		void setExecuteable() { permissions |= permissions_x; }
+		void setRelRo() { is_relro = true; }
+
+		void clearReadable() { permissions &= ~permissions_r; }
+		void clearWriteable() { permissions &= ~permissions_w; }
+		void clearExecuteable() { permissions &= ~permissions_x; }
+		void clearRelRo() { is_relro=false; }
+
+                std::string WriteToDB(File_t *fid, db_id_t newid);
+		std::string WriteToDBRange(File_t *fid, db_id_t newid, int start, int end, std::string table_name);
+
+	friend DataScoopByAddressComp_t;
+
+	private:
+		const static int permissions_r=4;
+		const static int permissions_w=2;
+		const static int permissions_x=1;
+
+		std::string name;
+		AddressID_t* start;
+		AddressID_t* end;
+		Type_t* type;
+		int permissions;
+		bool is_relro;
+		std::string contents;
+
+
+};
+
+class DataScoopByAddressComp_t {
+	public:
+	bool operator()(const DataScoop_t *lhs, const DataScoop_t *rhs) {
+
+		if (!lhs ||
+		    !rhs ||
+		    !lhs->start ||
+		    !rhs->start
+		   )
+			throw std::logic_error("Cannot order scoops that have null elements.");
+
+		return std::make_tuple(lhs->start->getVirtualOffset(), lhs) <
+		       std::make_tuple(rhs->start->getVirtualOffset(), rhs);
+	}
+};
+
+using DataScoopSet_t          = IRDB_SDK::DataScoopSet_t;
+using DataScoopByAddressSet_t = std::set<DataScoop_t*, DataScoopByAddressComp_t>;
+
+}
diff --git a/irdb-lib/libIRDB-core/include/transform_step.h b/irdb-lib/libIRDB-core/include/transform_step.h
new file mode 100644
index 0000000000000000000000000000000000000000..7e6d40926b5d577d2fc61001834dde4a669c7424
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/transform_step.h
@@ -0,0 +1,32 @@
+
+
+namespace libIRDB
+{
+	class TransformStep_t : virtual public IRDB_SDK::TransformStep_t
+	{
+		public:
+			// Step names must be unique, allows arguments to
+			// be directed to their matching transform steps.
+			virtual std::string getStepName(void) const = 0;
+
+			// Allows all steps to parse args before any step takes time to execute
+			virtual int parseArgs(const std::vector<std::string> step_args)
+			{
+				return 0; // success
+			}
+				
+			virtual int executeStep(IRDB_SDK::IRDBObjects_t *const irdb_objects)
+			{
+				return 0; // success
+			}
+			
+			virtual ~TransformStep_t(void)
+			{
+				// do nothing 
+			}		
+	};
+}
+
+extern "C"
+std::shared_ptr<IRDB_SDK::TransformStep_t> GetTransformStep(void);    
+
diff --git a/irdb-lib/libIRDB-core/include/type.hpp b/irdb-lib/libIRDB-core/include/type.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..da04eb8b8a8cc94e2a1f472ca484a47342c6fb2a
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/type.hpp
@@ -0,0 +1,143 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+using IRDB_Type    = IRDB_SDK::IRDBType_t;
+using TypeSet_t    = IRDB_SDK::TypeSet_t;
+using TypeVector_t = IRDB_SDK::TypeVector_t;
+
+class Type_t : public BaseObj_t, virtual public IRDB_SDK::Type_t
+{
+	public:
+		Type_t() : BaseObj_t(NULL) {
+			typeID = IRDB_SDK::itUnknown;
+		}	
+		Type_t(db_id_t dbid, IRDB_Type t, std::string n) : BaseObj_t(NULL) {
+			setBaseID(dbid);
+			typeID = t;
+			name = n;
+		}	
+		virtual ~Type_t() {}
+
+		virtual std::string WriteToDB(File_t *fid, db_id_t newid) = 0;
+
+		std::string getName() const { return name; }
+		void setName(const std::string& newname) { name=newname; }
+		IRDB_Type getTypeID() const { return typeID; }
+		void setTypeID(IRDB_Type t) { typeID = t; }
+
+		virtual bool isUnknownType() const { return typeID == IRDB_SDK::itUnknown; }
+		virtual bool isVariadicType() const { return typeID == IRDB_SDK::itVariadic; }
+		virtual bool isAggregateType() const { return typeID == IRDB_SDK::itAggregate; }
+		virtual bool isFuncType() const { return typeID == IRDB_SDK::itFunc; }
+		virtual bool isBasicType() const { return false; }
+		virtual bool isPointerType() const { return false; }
+		virtual bool isNumericType() const { return false; }
+
+	private:
+		std::string name;
+		IRDB_Type typeID;
+};
+
+class BasicType_t : public Type_t, virtual public IRDB_SDK::BasicType_t
+{
+	public:
+		BasicType_t() : Type_t() {}	
+		BasicType_t(db_id_t id, IRDB_Type type, std::string p_name) : Type_t(id, type, p_name) {}
+		virtual ~BasicType_t() {}
+
+		virtual bool isBasicType() const { return true; }
+		virtual bool isNumericType() const;
+
+		std::string WriteToDB(File_t *fid, db_id_t newid);
+};
+
+class PointerType_t : public Type_t, virtual public IRDB_SDK::PointerType_t
+{
+	public:
+		PointerType_t() : Type_t() { setTypeID(IRDB_SDK::itPointer); referentType = NULL; }	
+		PointerType_t(db_id_t id, Type_t* ref, std::string p_name) : Type_t(id, IRDB_SDK::itPointer, p_name) {
+			setReferentType(ref);
+		}
+		virtual ~PointerType_t() {}
+		virtual bool isPointerType() const { return true; }
+
+		IRDB_SDK::Type_t* getReferentType() const { return referentType; }
+		void setReferentType(IRDB_SDK::Type_t* r) { referentType = dynamic_cast<Type_t*>(r); if(r) assert(referentType); }
+
+		std::string WriteToDB(File_t *fid, db_id_t newid);
+
+	private:
+		Type_t* referentType; 
+};
+
+class AggregateType_t : public Type_t, virtual public IRDB_SDK::AggregateType_t
+{
+	public:
+		AggregateType_t() : Type_t() { setTypeID(IRDB_SDK::itAggregate); }	
+		AggregateType_t(db_id_t id, std::string p_name) : Type_t(id, IRDB_SDK::itAggregate, p_name) {}
+		virtual ~AggregateType_t() {}
+		virtual bool isAggregateType() const { return true; }
+
+		void addAggregatedType(IRDB_SDK::Type_t *t, int pos);
+		virtual size_t getNumAggregatedTypes() const { return refTypes.size(); } 
+		IRDB_SDK::Type_t* getAggregatedType(unsigned int pos) const { 
+			return (pos < (unsigned int)refTypes.size()) ? refTypes.at(pos) : NULL;
+		}
+
+		std::string toString() {
+			return getName();
+		}
+
+		std::string WriteToDB(File_t *fid, db_id_t newid);
+
+	private:
+		TypeVector_t refTypes;
+};
+
+class FuncType_t : public Type_t, virtual public IRDB_SDK::FuncType_t
+{
+	public:
+		FuncType_t() : Type_t() { setTypeID(IRDB_SDK::itFunc); _init(); }	
+		FuncType_t(db_id_t id, std::string p_name) : Type_t(id, IRDB_SDK::itFunc, p_name) { _init(); }
+		virtual ~FuncType_t() {}
+
+		virtual bool isFuncType() const { return true; }
+
+		std::string WriteToDB(File_t *fid, db_id_t newid);
+
+		IRDB_SDK::Type_t* getReturnType() const { return returnType; }
+		void setReturnType(IRDB_SDK::Type_t *t) { returnType = dynamic_cast<Type_t*>(t); if(t) assert(returnType); }
+		IRDB_SDK::AggregateType_t* getArgumentsType() const { return argsType; }
+		void setArgumentsType(IRDB_SDK::AggregateType_t *t) { argsType = dynamic_cast<AggregateType_t*>(t); if(t) assert(argsType);  }
+
+	private:
+		void _init() {
+			returnType = NULL;
+			argsType = NULL;
+		}
+
+	private:
+		Type_t*            returnType;
+		AggregateType_t*   argsType;
+};
+
+}
diff --git a/irdb-lib/libIRDB-core/include/variantid.hpp b/irdb-lib/libIRDB-core/include/variantid.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..578ff647efbc08183a6677b00c8af65cc217a165
--- /dev/null
+++ b/irdb-lib/libIRDB-core/include/variantid.hpp
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+namespace libIRDB
+{
+
+#define CURRENT_SCHEMA 2
+
+using FileSet_t = IRDB_SDK::FileSet_t;
+
+class VariantID_t : public BaseObj_t, virtual public IRDB_SDK::VariantID_t
+{
+    public:
+        VariantID_t();        		// create a Variant ID not in the database 
+        VariantID_t(db_id_t pid);       // read from the DB
+	~VariantID_t();     // Deletes the File_t objects -- beware dangling File_t* in FileIR_t objects!  
+
+        bool isRegistered() const;               
+        bool registerID();    // accesses DB
+
+	IRDB_SDK::VariantID_t* clone(bool deep=true);       // accesses DB
+
+	void WriteToDB();
+
+	void DropFromDB();
+
+	const FileSet_t&    getFiles() const { return files; }
+
+	std::string getName() const { return name; }
+	void setName(std::string newname) { name=newname;}
+
+	IRDB_SDK::File_t* getMainFile() const;
+
+
+	db_id_t getOriginalVariantID() const { return orig_pid;}
+	
+	void CloneFiles(FileSet_t& files);
+	File_t* CloneFile(File_t* fptr);
+
+    private:
+        schema_version_t schema_ver;
+        db_id_t orig_pid;       // matches pid if this is an "original"
+                                // Variant and not a cloned variant.
+
+        std::string name;
+
+	void CreateTables();	// create the address, function and instruction tables 
+
+        FileSet_t files;
+
+        void  ReadFilesFromDB();
+
+};
+
+
+
+
+}
+
diff --git a/irdb-lib/libIRDB-core/src/IRDB_Objects.cpp b/irdb-lib/libIRDB-core/src/IRDB_Objects.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..f61feee43be90c3164841e9ac71232492526bd08
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/IRDB_Objects.cpp
@@ -0,0 +1,255 @@
+#include <map>
+#include <libIRDB-core.hpp>
+#include <irdb-util>
+#include <utility>
+#include <memory>
+#include <algorithm>
+#include <assert.h>
+
+
+using namespace libIRDB;
+using namespace std;
+
+#define ALLOF(a) begin(a),end(a)
+
+
+IRDBObjects_t::~IRDBObjects_t()
+{
+        // All dynamically allocated DB objects
+        // are held as unique pointers and don't need to be 
+        // explicitly deleted.
+}
+
+IRDB_SDK::FileIR_t* IRDBObjects_t::addFileIR(const IRDB_SDK::DatabaseID_t variant_id, const IRDB_SDK::DatabaseID_t file_id)
+{
+        const auto it = file_IR_map.find(file_id);
+        
+        if(it == file_IR_map.end())
+        {
+		return nullptr;
+        }
+        else
+        {           
+		const auto the_file = (it->second).file;
+		auto& the_fileIR = (it->second).fileIR;
+
+		if(the_fileIR == NULL)
+		{
+			assert(the_file != NULL);
+
+			assert(variant_map.find(variant_id) != variant_map.end());
+			const auto & the_variant = *(variant_map.at(variant_id).get());
+
+			the_fileIR = unique_ptr<FileIR_t>(new FileIR_t(the_variant, the_file));
+			assert(the_fileIR != NULL);
+		}
+
+		// make sure static variable is set in the calling module -- IMPORTANT
+		the_fileIR->setArchitecture();
+		return the_fileIR.get();
+        }
+}
+
+int IRDBObjects_t::writeBackFileIR(const IRDB_SDK::DatabaseID_t file_id, ostream *verbose_logging)
+{
+        const auto it = file_IR_map.find(file_id);
+        
+        if(it == file_IR_map.end())
+            return 1; 
+ 
+        const auto& the_file = (it->second).file;
+        assert(the_file != NULL);
+                    
+	try
+	{
+		// cout<<"Writing changes for "<<the_file->getURL()<<endl;
+		// make sure static variable is set in the calling module -- IMPORTANT
+		const auto & the_fileIR = (it->second).fileIR;
+		the_fileIR->setArchitecture();
+		the_fileIR->writeToDB(verbose_logging);
+        	return 0;
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cerr << "Unexpected database error: " << pnide << "file url: " << the_file->getURL() << endl;
+		return -1;
+	}
+	catch (...)
+	{
+		cerr << "Unexpected error file url: " << the_file->getURL() << endl;
+		return -1;
+	}
+	assert(0); // should not reach
+        
+}
+
+void IRDBObjects_t::deleteFileIR(const IRDB_SDK::DatabaseID_t file_id)
+{
+        const auto it = file_IR_map.find(file_id);
+        
+        if(it == file_IR_map.end())
+		return;
+
+	auto& the_fileIR = (it->second).fileIR;
+	if(the_fileIR != NULL)
+	{
+		the_fileIR.reset();
+	}
+}
+
+bool IRDBObjects_t::filesAlreadyPresent(const FileSet_t& the_files) const
+{
+	// look for a missing file
+	const auto missing_file_it=find_if(ALLOF(the_files), [&](const IRDB_SDK::File_t* const f)
+		{
+			return (file_IR_map.find(f->getBaseID()) == file_IR_map.end());
+		});
+        
+	// return true if no files missing
+        return missing_file_it==the_files.end();
+}
+
+IRDB_SDK::VariantID_t* IRDBObjects_t::addVariant(const IRDB_SDK::DatabaseID_t variant_id)
+{
+        const auto var_it = variant_map.find(variant_id);      
+
+        if(var_it != variant_map.end())
+        {
+            return (var_it->second).get();
+        }
+
+	variant_map[variant_id].reset(new VariantID_t(variant_id));	
+	auto the_variant = variant_map[variant_id].get();
+
+	assert(the_variant->isRegistered()==true);
+	// disallow variants that share shallow copies to both be read in
+        // to prevent desynchronization. 
+        assert(!filesAlreadyPresent(the_variant->getFiles()));
+
+        // add files
+	for(auto &curr_file : the_variant->getFiles())
+	{
+            file_IR_map[curr_file->getBaseID()]=FileIRInfo_t();
+	    file_IR_map[curr_file->getBaseID()].file = dynamic_cast<File_t*>(curr_file);
+        }
+        
+        return the_variant;
+}
+
+
+int IRDBObjects_t::writeBackVariant(const IRDB_SDK::DatabaseID_t variant_id)
+{
+        const auto it = variant_map.find(variant_id);
+        
+        if(it == variant_map.end())
+		return 1;
+
+	try
+	{
+		// cout<<"Writing changes for variant "<<variant_id<<endl;
+		it->second->WriteToDB();
+        	return 0;
+	}
+	catch (DatabaseError_t pnide)
+	{
+		cerr << "Unexpected database error: " << pnide << "variant ID: " << variant_id << endl;
+		return -1;
+	}
+	catch (...)
+	{
+		cerr << "Unexpected error variant ID: " << variant_id << endl;
+		return -1;
+	}
+	assert(0); // unreachable.
+        
+}
+
+void IRDBObjects_t::deleteVariant(const IRDB_SDK::DatabaseID_t variant_id)
+{
+        const auto var_it = variant_map.find(variant_id);
+        
+        if(var_it == variant_map.end())
+		return;
+
+	// remove files and file IRs
+	for(const auto file : var_it->second->getFiles())
+	{
+		file_IR_map.erase(file->getBaseID());
+	}
+    
+	// remove variant
+	variant_map.erase(variant_id);
+}
+
+int IRDBObjects_t::writeBackAll(ostream *verbose_logging)
+{
+        int ret_status = 0;
+
+        // Write back FileIRs
+	for(auto &file_pair : file_IR_map)
+        {
+		const int result = IRDBObjects_t::writeBackFileIR((file_pair.second.file)->getBaseID(), verbose_logging);
+		if(result != 0)
+		{
+			ret_status = -1;
+		}
+        }
+
+        // Write back Variants
+	for(auto & variant_pair : variant_map)
+        {
+		const int result = IRDBObjects_t::writeBackVariant((variant_pair.second)->getBaseID());
+		if(result != 0)
+		{
+			ret_status = -1;
+		}
+        }
+        return ret_status;
+}
+
+void IRDBObjects_t::deleteAll(void)
+{
+        // Delete Variants (also deletes all files)
+	for( auto &variant_pair : variant_map)
+        {
+		IRDBObjects_t::deleteVariant((variant_pair.second)->getBaseID());
+        }
+}
+
+IRDB_SDK::pqxxDB_t* IRDBObjects_t::getDBInterface() const
+{
+        return pqxx_interface.get();
+}
+
+IRDB_SDK::pqxxDB_t* IRDBObjects_t::resetDBInterface()
+{
+	pqxx_interface.reset(new pqxxDB_t());  // Aborts if Commit() has not been called
+	BaseObj_t::setInterface(pqxx_interface.get());
+	return pqxx_interface.get();
+}
+
+
+void IRDBObjects_t::tidyIR(void)
+{
+        // Delete Variants (also deletes all files)
+	for( auto &variant_pair : file_IR_map)
+        {
+		const auto &file_ir_info = variant_pair.second;
+		auto fileIR=file_ir_info.fileIR.get();
+		fileIR->assembleRegistry();
+		fileIR->setBaseIDS();
+        }
+}
+
+void FileIR_t::moveRelocation(IRDB_SDK::Relocation_t* reloc, IRDB_SDK::Instruction_t* from, IRDB_SDK::Instruction_t* to) 
+{
+	auto irdb_from=dynamic_cast<libIRDB::Instruction_t*>(from);
+	auto irdb_to  =dynamic_cast<libIRDB::Instruction_t*>(to);
+
+	irdb_to  ->GetRelocations().insert(reloc);
+	irdb_from->GetRelocations().erase (reloc);
+
+
+
+}
+
diff --git a/irdb-lib/libIRDB-core/src/SConscript b/irdb-lib/libIRDB-core/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..a98b3d156e385fe8ccc4ceeb536ca852bcd7969f
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/SConscript
@@ -0,0 +1,63 @@
+import os
+import glob
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+libname="irdb-core"
+files=  '''
+	address.cpp
+	baseobj.cpp
+	dbinterface.cpp
+	file.cpp
+	fileir.cpp
+	function.cpp
+	generate_spri.cpp
+	icfs.cpp
+	instruction.cpp
+	pqxxdb.cpp
+	type.cpp
+	scoop.cpp
+	variantid.cpp
+	eh.cpp
+	reloc.cpp
+	decode_csx86.cpp
+	operand_csx86.cpp
+	decode_csarm.cpp
+	operand_csarm.cpp
+	IRDB_Objects.cpp
+	decode_base.cpp
+'''
+unused_files='''
+	decode_bea.cpp
+	operand_bea.cpp
+	'''
+
+# bea engine listed for core components.
+
+cpppath=''' 
+	.
+	$IRDB_SDK/include/
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-core/include/
+	$SECURITY_TRANSFORMS_HOME/libcapstone/include/capstone/
+	'''
+libpath='''
+	$SECURITY_TRANSFORMS_HOME/lib
+        '''
+
+#globs=glob.glob(os.environ['SECURITY_TRANSFORMS_HOME']+'/libcapstone/zipr_unpack/*.o')
+
+myenv.Append(CCFLAGS=" -Wall -std=c++11 -fmax-errors=2 ")
+myenv.Append(LIBPATH=libpath)
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+mylib=myenv.SharedLibrary(libname, Split(files), LIBS=Split("pqxx capstone"))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", mylib)
+Default(install)
+
+Return('install')
+
diff --git a/irdb-lib/libIRDB-core/src/SConstruct b/irdb-lib/libIRDB-core/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b2e8e0ca9b3cfeb2a49f186cdc49b783f79c5adb
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/SConstruct
@@ -0,0 +1,9 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return('lib')
+
diff --git a/irdb-lib/libIRDB-core/src/address.cpp b/irdb-lib/libIRDB-core/src/address.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..cb5bb7ebb755a51270bf2145f2b894aff2c1207d
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/address.cpp
@@ -0,0 +1,56 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <all.hpp>
+#include <irdb-util>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+
+vector<string> AddressID_t::WriteToDB(File_t *fid, db_id_t newid, bool p_withHeader)
+{
+        assert(fid);
+	
+	if(getBaseID()==NOT_IN_DATABASE)
+		setBaseID(newid);
+
+/*
+	string q;
+	if (p_withHeader)
+        q=string("insert into ")+fid->address_table_name + 
+			string("(address_id , file_id , vaddress_offset , doip_id)") +
+			string(" values ");
+	else
+		q = ",";
+			
+	q +=
+*/
+	return {
+		to_string(getBaseID()),
+		to_string(fileID),
+		to_string(virtual_offset),
+		to_string(getDoipID())
+		};
+
+}
+
diff --git a/irdb-lib/libIRDB-core/src/all.hpp b/irdb-lib/libIRDB-core/src/all.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..ec6b27114c86012d806295c583494384ad7dd980
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/all.hpp
@@ -0,0 +1,22 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <libIRDB-core.hpp> 
+using namespace libIRDB;
diff --git a/irdb-lib/libIRDB-core/src/baseobj.cpp b/irdb-lib/libIRDB-core/src/baseobj.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..90cef65fdb8e19e1a20240f196cea48ca6633050
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/baseobj.cpp
@@ -0,0 +1,47 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <all.hpp>
+
+
+/*
+ * initialize the DB interface
+ */
+DBinterface_t* BaseObj_t::dbintr=nullptr;
+const db_id_t IRDB_SDK::BaseObj_t::NOT_IN_DATABASE=-1;
+
+/* 
+ * BaseObj_t constructor
+ */
+BaseObj_t::BaseObj_t(doip_t* _doip) : doip(_doip), base_id(BaseObj_t::NOT_IN_DATABASE) 
+{
+}
+
+
+/* 
+ * Set the database interface to be used for the base object class.
+ */
+void IRDB_SDK::BaseObj_t::setInterface(IRDB_SDK::DBinterface_t *dbi)
+{
+	::libIRDB::BaseObj_t::dbintr=dynamic_cast<libIRDB::DBinterface_t*>(dbi);
+	assert(::libIRDB::BaseObj_t::dbintr);
+}
+
diff --git a/irdb-lib/libIRDB-core/src/dbinterface.cpp b/irdb-lib/libIRDB-core/src/dbinterface.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..f408adb289669812df763c1ea5bdb82eebef7acf
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/dbinterface.cpp
@@ -0,0 +1,53 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <all.hpp>
+#include <iostream>
+#include <stdlib.h>
+
+using namespace std;
+
+ostream& libIRDB::operator<<(ostream& output, const libIRDB::DatabaseError_t& p)
+{
+	switch(p.GetErrorCode())
+	{
+		case DatabaseError_t::VariantTableNotRegistered:
+			output<<"Error accessing variant_info table";
+			break;
+		case DatabaseError_t::VariantNotInDatabase:
+			output<<"Variant not detected in database";
+			break;
+		default:
+			output<<"Cannot print database error code.";
+			break;
+	}
+	return output;
+}
+
+ostream& IRDB_SDK::operator<<(ostream& output, const IRDB_SDK::DatabaseError_t& p)
+{
+	const auto p_p = &p;
+	const auto real_p=dynamic_cast<const libIRDB::DatabaseError_t* const>(p_p);
+	assert(real_p);
+	output << *real_p;
+	return output;
+}
+
diff --git a/irdb-lib/libIRDB-core/src/decode_base.cpp b/irdb-lib/libIRDB-core/src/decode_base.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..25e996b556c895ec1755e67804667818d5d279c3
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/decode_base.cpp
@@ -0,0 +1,43 @@
+
+#include <libIRDB-core.hpp>
+#include <decode_base.hpp>
+#include <operand_base.hpp>
+#include <decode_csx86.hpp>
+#include <operand_csx86.hpp>
+#include <decode_csarm.hpp>
+#include <operand_csarm.hpp>
+#include <exception>
+
+using namespace std;
+using namespace libIRDB;
+
+
+unique_ptr<IRDB_SDK::DecodedInstruction_t> IRDB_SDK::DecodedInstruction_t::factory(const IRDB_SDK::Instruction_t* p_i)
+{
+	const auto i=dynamic_cast<const libIRDB::Instruction_t*>(p_i);
+	assert(i);
+	auto op=IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtAarch64 ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneARM64_t(i) : 
+		IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtX86_64  ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneX86_t  (i) : 
+		IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtI386    ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneX86_t  (i) : 
+		throw invalid_argument("Unknown machine type");
+	return unique_ptr<DecodedInstruction_t>(op);
+}
+
+unique_ptr<IRDB_SDK::DecodedInstruction_t> IRDB_SDK::DecodedInstruction_t::factory(const IRDB_SDK::VirtualOffset_t start_addr, const void *data, uint32_t max_len)
+{
+	auto op=IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtAarch64 ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneARM64_t(start_addr,data,max_len) : 
+		IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtX86_64  ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneX86_t  (start_addr,data,max_len) : 
+		IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtI386    ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneX86_t  (start_addr,data,max_len) : 
+		throw invalid_argument("Unknown machine type");
+	return unique_ptr<DecodedInstruction_t>(op);
+}
+
+unique_ptr<IRDB_SDK::DecodedInstruction_t> IRDB_SDK::DecodedInstruction_t::factory(const IRDB_SDK::VirtualOffset_t start_addr, const void *data, const void* endptr)
+{
+	auto op=IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtAarch64 ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneARM64_t(start_addr,data,endptr) : 
+		IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtX86_64  ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneX86_t  (start_addr,data,endptr) : 
+		IRDB_SDK::FileIR_t::getArchitecture()->getMachineType()==IRDB_SDK::admtI386    ? (IRDB_SDK::DecodedInstruction_t*)new DecodedInstructionCapstoneX86_t  (start_addr,data,endptr) : 
+		throw invalid_argument("Unknown machine type");
+	return unique_ptr<DecodedInstruction_t>(op);
+}
+
diff --git a/irdb-lib/libIRDB-core/src/decode_csarm.cpp b/irdb-lib/libIRDB-core/src/decode_csarm.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..497d92b2abdfc0f5d903baac223fc2e388b1253a
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/decode_csarm.cpp
@@ -0,0 +1,364 @@
+
+#include <libIRDB-core.hpp>
+#include <decode_base.hpp>
+#include <decode_csarm.hpp>
+#include <operand_base.hpp>
+#include <operand_csarm.hpp>
+
+
+#include <capstone.h>
+#include <arm64.h>
+#include <string>
+#include <functional>
+#include <set>
+#include <algorithm>
+#include <stdexcept>
+
+using namespace libIRDB;
+using namespace std;
+
+#define ALLOF(a) begin(a),end(a)
+static const auto ARM64_REG_PC=(arm64_reg)(ARM64_REG_ENDING+1);
+
+
+DecodedInstructionCapstoneARM64_t::CapstoneHandle_t* DecodedInstructionCapstoneARM64_t::cs_handle=NULL ;
+
+DecodedInstructionCapstoneARM64_t::CapstoneHandle_t::CapstoneHandle_t(FileIR_t* firp)
+{
+	const auto mode = CS_MODE_LITTLE_ENDIAN;
+	static_assert(sizeof(csh)==sizeof(handle), "Capstone handle size is unexpected.  Has CS changed?");
+	auto err = cs_open(CS_ARCH_ARM64, mode,  (csh*)&handle);
+
+	if (err)
+	{
+		const auto s=string("Failed on cs_open() with error returned: ")+to_string(err)+"\n";
+		throw std::runtime_error(s);
+	}
+	cs_option(handle, CS_OPT_DETAIL, CS_OPT_ON);
+	cs_option(handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_INTEL);
+
+
+}
+
+
+
+
+static bool isPartOfGroup(const cs_insn* the_insn, const arm64_insn_group the_grp) 
+{
+	const auto grp_it=find(ALLOF(the_insn->detail->groups), the_grp);
+	return grp_it!=end(the_insn->detail->groups);
+
+}
+
+static bool isJmp(cs_insn* the_insn) 
+{
+	return isPartOfGroup(the_insn,ARM64_GRP_JUMP);
+}
+
+
+template<class type>
+static inline type insnToImmedHelper(cs_insn* the_insn, csh handle)
+{
+        const auto count = cs_op_count(handle, the_insn, ARM64_OP_IMM);
+	const auto arm = &(the_insn->detail->arm64);
+
+        if (count==0) 
+		return 0;	 /* no immediate is the same as an immediate of 0, i guess? */
+        else if (count==1) 
+	{
+		const auto index = cs_op_index(handle, the_insn, ARM64_OP_IMM, 1);
+		return arm->operands[index].imm;
+	}
+	else
+		throw std::logic_error(string("Called ")+__FUNCTION__+" with number of immedaites not equal 1");
+}
+
+
+
+// shared code 
+// constructors, destructors, operators.
+
+void DecodedInstructionCapstoneARM64_t::Disassemble(const virtual_offset_t start_addr, const void *data, const uint32_t max_len)
+{
+	using namespace std::placeholders;
+	auto insn=cs_malloc(cs_handle->getHandle());
+	auto address=(uint64_t)start_addr;
+	auto size=(size_t)max_len;
+	const uint8_t* code=(uint8_t*)data;
+	const auto ok = cs_disasm_iter(cs_handle->getHandle(), &code, &size, &address, insn);
+	if(!ok)
+		insn->size=0;
+
+        auto &op0 = (insn->detail->arm64.operands[0]); // might change these.
+        auto &op1 = (insn->detail->arm64.operands[1]);
+
+	const auto mnemonic=string(insn->mnemonic);
+	const auto is_ldr_type = mnemonic=="ldr"  || mnemonic=="ldrsw" ;
+	if(is_ldr_type && op1.type==ARM64_OP_IMM)
+	{
+		// no, this is a pcrel load.
+		const auto imm=op1.imm;
+		op1.type=ARM64_OP_MEM;
+		op1.mem.base=ARM64_REG_PC;
+		op1.mem.index=ARM64_REG_INVALID;
+		op1.mem.disp=imm;
+	}
+	if(mnemonic=="prfm" && op0.type==ARM64_OP_IMM)
+	{
+		// no, this is a pcrel load.
+		const auto imm=op0.imm;
+		op0.type=ARM64_OP_MEM;
+		op0.mem.base=ARM64_REG_PC;
+		op0.mem.index=ARM64_REG_INVALID;
+		op0.mem.disp=imm;
+	}
+
+
+	const auto cs_freer=[](cs_insn * insn) -> void 
+		{  
+			cs_free(insn,1); 
+		} ; 
+	my_insn.reset(insn,cs_freer);
+}
+
+DecodedInstructionCapstoneARM64_t::DecodedInstructionCapstoneARM64_t(const Instruction_t* i)
+{
+	if(!cs_handle) cs_handle=new CapstoneHandle_t(NULL);
+	if(!i) throw std::invalid_argument("No instruction given to DecodedInstruction_t(Instruction_t*)");
+
+        const auto length=i->getDataBits().size();
+	const auto &databits=i->getDataBits();
+	const auto data=databits.data();
+	const auto address=i->getAddress()->getVirtualOffset();
+        Disassemble(address,data,length);
+
+	if(!valid()) throw std::invalid_argument("The Instruction_t::getDataBits field is not a valid instruction.");
+}
+
+DecodedInstructionCapstoneARM64_t::DecodedInstructionCapstoneARM64_t(const virtual_offset_t start_addr, const void *data, uint32_t max_len)
+{
+	if(!cs_handle) cs_handle=new CapstoneHandle_t(NULL);
+        Disassemble(start_addr, data, max_len);
+}
+
+DecodedInstructionCapstoneARM64_t::DecodedInstructionCapstoneARM64_t(const virtual_offset_t start_addr, const void *data, const void* endptr)
+{
+	if(!cs_handle) cs_handle=new CapstoneHandle_t(NULL);
+        const auto length=(char*)endptr-(char*)data;
+        Disassemble(start_addr,data,length);
+}
+
+DecodedInstructionCapstoneARM64_t::DecodedInstructionCapstoneARM64_t(const DecodedInstructionCapstoneARM64_t& copy)
+{
+	*this=copy;
+}
+
+DecodedInstructionCapstoneARM64_t::DecodedInstructionCapstoneARM64_t(const shared_ptr<void> &p_my_insn)
+	: my_insn(p_my_insn)
+{
+}
+
+DecodedInstructionCapstoneARM64_t::~DecodedInstructionCapstoneARM64_t()
+{
+	// no need to cs_free(my_insn) because shared pointer will do that for us!
+}
+
+DecodedInstructionCapstoneARM64_t& DecodedInstructionCapstoneARM64_t::operator=(const DecodedInstructionCapstoneARM64_t& copy)
+{
+	my_insn=copy.my_insn;
+	return *this;
+}
+
+// public methods
+
+string DecodedInstructionCapstoneARM64_t::getDisassembly() const
+{
+
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	auto full_str=getMnemonic()+" "+the_insn->op_str;
+
+	return full_str;
+}
+
+bool DecodedInstructionCapstoneARM64_t::valid() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return the_insn->size!=0;
+}
+
+uint32_t DecodedInstructionCapstoneARM64_t::length() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return the_insn->size;
+}
+
+bool DecodedInstructionCapstoneARM64_t::isBranch() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isCall() || isReturn() || isJmp(the_insn);
+}
+
+bool DecodedInstructionCapstoneARM64_t::isCall() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto mnemonic=getMnemonic();
+	return mnemonic=="bl" || mnemonic=="blr";
+}
+
+bool DecodedInstructionCapstoneARM64_t::isUnconditionalBranch() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	return isJmp(the_insn) && 
+		(getMnemonic()=="b" || getMnemonic()=="br");
+}
+
+bool DecodedInstructionCapstoneARM64_t::isConditionalBranch() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isJmp(the_insn) && !isUnconditionalBranch();
+}
+
+bool DecodedInstructionCapstoneARM64_t::isReturn() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isPartOfGroup(the_insn,ARM64_GRP_RET);
+}
+
+bool DecodedInstructionCapstoneARM64_t::hasOperand(const int op_num) const
+{
+	if(op_num<0) throw std::logic_error(string("Called ")+ __FUNCTION__+" with opnum="+to_string(op_num));
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	const auto &arm = (the_insn->detail->arm64);
+	return 0 <= op_num  && op_num < arm.op_count;
+}
+
+// 0-based.  first operand is numbered 0.
+shared_ptr<DecodedOperand_t> DecodedInstructionCapstoneARM64_t::getOperand(const int op_num) const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	if(!hasOperand(op_num)) throw std::logic_error(string("Called ")+__FUNCTION__+" on without hasOperand()==true");
+
+	return shared_ptr<DecodedOperand_t>(new DecodedOperandCapstoneARM64_t(my_insn,(uint8_t)op_num));
+	
+}
+
+DecodedOperandVector_t DecodedInstructionCapstoneARM64_t::getOperands() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	const auto &arm = (the_insn->detail->arm64);
+	const auto opcount=arm.op_count;
+
+	auto ret_val=DecodedOperandVector_t();
+	
+	for(auto i=0;i<opcount;i++)
+		ret_val.push_back(getOperand(i));
+
+	return ret_val;
+}
+
+string DecodedInstructionCapstoneARM64_t::getMnemonic() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	// return the new string.
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return the_insn->mnemonic;
+
+	
+}
+
+
+int64_t DecodedInstructionCapstoneARM64_t::getImmediate() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	// direct calls and jumps have a "immediate" which is really an address"  those are returned by getAddress
+	if(isCall() || isJmp(the_insn))
+		return 0;
+
+	return insnToImmedHelper<int64_t>(the_insn, cs_handle->getHandle());
+}
+
+
+virtual_offset_t DecodedInstructionCapstoneARM64_t::getAddress() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	if(isCall() || isJmp(the_insn))
+	{
+		const auto mnemonic=getMnemonic();
+		if( mnemonic=="tbnz" || mnemonic=="tbz")
+			return getOperand(2)->getConstant();
+		return insnToImmedHelper<int64_t>(the_insn, cs_handle->getHandle());
+	}
+	assert(0);
+
+}
+
+
+bool DecodedInstructionCapstoneARM64_t::setsStackPointer() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	if(!hasOperand(0)) return false;
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	const auto &arm = (the_insn->detail->arm64);
+	return (arm.operands[0].type==ARM64_OP_REG && arm.operands[0].reg==ARM64_REG_SP);
+}
+
+uint32_t DecodedInstructionCapstoneARM64_t::getPrefixCount() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	return 0;
+}
+
+IRDB_SDK::VirtualOffset_t DecodedInstructionCapstoneARM64_t::getMemoryDisplacementOffset(const IRDB_SDK::DecodedOperand_t* t, const IRDB_SDK::Instruction_t* insn) const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	assert(0);
+}
+
+
+
+bool DecodedInstructionCapstoneARM64_t::hasRelevantRepPrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	return false;
+}
+
+bool DecodedInstructionCapstoneARM64_t::hasRelevantRepnePrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	return false;
+}
+
+bool DecodedInstructionCapstoneARM64_t::hasRelevantOperandSizePrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	return false;
+}
+
+bool DecodedInstructionCapstoneARM64_t::hasRexWPrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	return false;
+}
+
+bool DecodedInstructionCapstoneARM64_t::hasImplicitlyModifiedRegs() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	return false;
+}
+
diff --git a/irdb-lib/libIRDB-core/src/decode_csx86.cpp b/irdb-lib/libIRDB-core/src/decode_csx86.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..c261c069e16dfca79dc32f723d2b53337adb4f31
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/decode_csx86.cpp
@@ -0,0 +1,712 @@
+
+#include <libIRDB-core.hpp>
+#include <decode_base.hpp>
+#include <decode_csx86.hpp>
+#include <operand_base.hpp>
+#include <operand_csx86.hpp>
+
+#include <capstone.h>
+#include <x86.h>
+#include <string>
+#include <functional>
+#include <set>
+#include <algorithm>
+#include <stdexcept>
+
+using namespace libIRDB;
+using namespace std;
+
+#define ALLOF(a) begin(a),end(a)
+
+
+
+DecodedInstructionCapstoneX86_t::CapstoneHandle_t* DecodedInstructionCapstoneX86_t::cs_handle=NULL ;
+
+DecodedInstructionCapstoneX86_t::CapstoneHandle_t::CapstoneHandle_t(FileIR_t* firp)
+{
+	const auto width=FileIR_t::getArchitectureBitWidth();
+	const auto mode = (width==64) ? CS_MODE_64: CS_MODE_32;
+	static_assert(sizeof(csh)==sizeof(handle), "Capstone handle size is unexpected.  Has CS changed?");
+	auto err = cs_open(CS_ARCH_X86, mode,  (csh*)&handle);
+
+	if (err)
+	{
+		const auto s=string("Failed on cs_open() with error returned: ")+to_string(err)+"\n";
+		throw std::runtime_error(s);
+	}
+	cs_option(handle, CS_OPT_DETAIL, CS_OPT_ON);
+	cs_option(handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_INTEL);
+
+
+}
+
+
+
+typedef struct special_instruction special_instruction_t;
+struct special_instruction
+{
+	string binary;
+	string mnemonic;
+	string operands;
+};
+
+vector<special_instruction_t> cs_special_instructions=
+	{
+		{"\xdf\xc0", "ffreep", "st0"}
+	};
+
+
+// static helpers 
+static inline bool hasPrefix(const cs_insn* the_insn, const x86_prefix desired_pref)
+{
+	const auto count=count_if(ALLOF(the_insn->detail->x86.prefix), [&](const uint8_t actual_pref) { return actual_pref==desired_pref; } ) ;
+	return count!=0;
+}
+
+static bool isPartOfGroup(const cs_insn* the_insn, const x86_insn_group the_grp) 
+{
+	const auto grp_it=find(ALLOF(the_insn->detail->groups), the_grp);
+	return grp_it!=end(the_insn->detail->groups);
+
+}
+
+static bool isJmp(cs_insn* the_insn) 
+{
+	return isPartOfGroup(the_insn,X86_GRP_JUMP);
+}
+
+#if 0
+class CapstoneHandle_t
+{
+	public:
+		CapstoneHandle_t(FileIR_t* firp=NULL)
+		{
+
+			const auto width=FileIR_t::getArchitectureBitWidth();
+			const auto mode = (width==64) ? CS_MODE_64: CS_MODE_32; 
+	                auto err = cs_open(CS_ARCH_X86, mode,  &handle);
+
+			if (err) 
+			{
+				const auto s=string("Failed on cs_open() with error returned: ")+to_string(err)+"\n";
+				throw std::runtime_error(s);
+			}
+                	cs_option(handle, CS_OPT_DETAIL, CS_OPT_ON);
+			cs_option(handle, CS_OPT_SYNTAX, CS_OPT_SYNTAX_INTEL);
+
+
+		}
+		inline csh getHandle() { return handle; }
+
+	private:
+		csh handle;
+};
+static CapstoneHandle_t *cs_handle=NULL;
+#endif
+
+template<class type>
+static inline type insnToImmedHelper(cs_insn* the_insn, csh handle)
+{
+        const auto count = cs_op_count(handle, the_insn, X86_OP_IMM);
+	const auto x86 = &(the_insn->detail->x86);
+
+        if (count==0) 
+		return 0;	 /* no immediate is the same as an immediate of 0, i guess? */
+        else if (count==1) 
+	{
+		const auto index = cs_op_index(handle, the_insn, X86_OP_IMM, 1);
+		return x86->operands[index].imm;
+	}
+	else
+		throw std::logic_error(string("Called ")+__FUNCTION__+" with number of immedaites not equal 1");
+}
+
+
+
+// shared code 
+// constructors, destructors, operators.
+
+void DecodedInstructionCapstoneX86_t::Disassemble(const virtual_offset_t start_addr, const void *data, const uint32_t max_len)
+{
+	using namespace std::placeholders;
+	auto insn=cs_malloc(cs_handle->getHandle());
+	auto address=(uint64_t)start_addr;
+	auto size=(size_t)max_len;
+	const uint8_t* code=(uint8_t*)data;
+	const auto ok = cs_disasm_iter(cs_handle->getHandle(), &code, &size, &address, insn);
+	if(!ok)
+		insn->size=0;
+
+
+	if(insn->size==0)
+	{
+		const auto special_it=find_if(ALLOF(cs_special_instructions), [&](const special_instruction_t& si)
+			{
+				if(si.binary.length() > max_len)
+					return false;
+				const auto data_as_str=string((char*)data,si.binary.length());
+				return si.binary==data_as_str;
+			});
+		const auto is_special=special_it != end(cs_special_instructions);
+		if(is_special)
+		{
+			// if we run into more complicated stuff, we may need to extend this
+			insn->size=special_it->binary.length();
+			strcpy(insn->mnemonic, special_it->mnemonic.c_str());
+			strcpy(insn->op_str, special_it->operands.c_str());
+		}
+	
+	}
+
+	const auto mnemonic=string(insn->mnemonic);
+
+	const auto x86=insn->detail->x86;
+
+	if(mnemonic=="fcompi")
+		strcpy(insn->mnemonic, "fcomip"); // bad opcode out of capstone.
+	else if(x86.opcode[0]==0xa5 && string(insn->mnemonic)=="movsq")
+		strcpy(insn->op_str, ""); // force into MOVS version
+	// note, there's two forms of movsd -- one is move string, the other is move scalar double, 
+	// only adjust the move string version  
+	else if(x86.opcode[0]==0xa4 && string(insn->mnemonic)=="movsd")	 
+		strcpy(insn->op_str, ""); // force into MOVS version
+	else if(x86.opcode[0]==0xa5 && string(insn->mnemonic)=="movsw")
+		strcpy(insn->op_str, ""); // force into MOVS version
+	else if(x86.opcode[0]==0xa4 && string(insn->mnemonic)=="movsb")
+		strcpy(insn->op_str, ""); // force into MOVS version
+
+/*
+	if(mnemonic=="movabs")
+	{
+		if(insn->detail->x86.operands[0].type==X86_OP_MEM)
+		{
+			insn->detail->x86.operands[0].imm=insn->detail->x86.operands[0].mem.disp;
+			insn->detail->x86.operands[0].type=X86_OP_IMM;
+		}
+		if(insn->detail->x86.operands[1].type==X86_OP_MEM)
+		{
+			insn->detail->x86.operands[1].imm=insn->detail->x86.operands[1].mem.disp;
+			insn->detail->x86.operands[1].type=X86_OP_IMM;
+		}
+	}
+*/
+
+	const auto cs_freer=[](cs_insn * insn) -> void 
+		{  
+			cs_free(insn,1); 
+		} ; 
+	my_insn.reset(insn,cs_freer);
+}
+
+DecodedInstructionCapstoneX86_t::DecodedInstructionCapstoneX86_t(const Instruction_t* i)
+{
+	if(!cs_handle) cs_handle=new CapstoneHandle_t(NULL);
+	if(!i) throw std::invalid_argument("No instruction given to DecodedInstruction_t(Instruction_t*)");
+
+        const auto length=i->getDataBits().size();
+	const auto &databits=i->getDataBits();
+	const auto data=databits.data();
+	const auto address=i->getAddress()->getVirtualOffset();
+        Disassemble(address,data,length);
+
+	if(!valid()) throw std::invalid_argument("The Instruction_t::getDataBits field is not a valid instruction.");
+}
+
+DecodedInstructionCapstoneX86_t::DecodedInstructionCapstoneX86_t(const virtual_offset_t start_addr, const void *data, uint32_t max_len)
+{
+	if(!cs_handle) cs_handle=new CapstoneHandle_t(NULL);
+        Disassemble(start_addr, data, max_len);
+}
+
+DecodedInstructionCapstoneX86_t::DecodedInstructionCapstoneX86_t(const virtual_offset_t start_addr, const void *data, const void* endptr)
+{
+	if(!cs_handle) cs_handle=new CapstoneHandle_t(NULL);
+        const auto length=(char*)endptr-(char*)data;
+        Disassemble(start_addr,data,length);
+}
+
+DecodedInstructionCapstoneX86_t::DecodedInstructionCapstoneX86_t(const DecodedInstructionCapstoneX86_t& copy)
+{
+	*this=copy;
+}
+
+DecodedInstructionCapstoneX86_t::DecodedInstructionCapstoneX86_t(const shared_ptr<void> &p_my_insn)
+	: my_insn(p_my_insn)
+{
+}
+
+DecodedInstructionCapstoneX86_t::~DecodedInstructionCapstoneX86_t()
+{
+	// no need to cs_free(my_insn) because shared pointer will do that for us!
+}
+
+DecodedInstructionCapstoneX86_t& DecodedInstructionCapstoneX86_t::operator=(const DecodedInstructionCapstoneX86_t& copy)
+{
+	my_insn=copy.my_insn;
+	return *this;
+}
+
+// public methods
+
+string DecodedInstructionCapstoneX86_t::getDisassembly() const
+{
+	const auto myReplace=[](std::string &str,
+		       const std::string& oldStr,
+		       const std::string& newStr) -> void
+	{
+		std::string::size_type pos = 0u;
+		while((pos = str.find(oldStr, pos)) != std::string::npos)
+		{
+			str.replace(pos, oldStr.length(), newStr);
+			pos += newStr.length();
+		}
+	};
+
+
+	// a list of special mnemonics that can't have a mem decoration because nasm sux.
+	const auto no_memdec_mnemonics=set<string>(
+		{
+		"lea",
+		"movd",
+		"pinsrw",
+		"psllw",
+		"pslld",
+		"psllq",
+		"psrlw",
+		"psrld",
+		"psrlq",
+		"psraw",
+		"psrad",
+		});
+
+
+	// a list of prefixes and suffixes of mnemonics that can't have a mem decoration because nasm sux.
+	// helps deal with things like {mov,add,sub,mul,div, cmp}*{ss,sd,pd,pq}, esp when the cmp has a 
+	// {l,le,ne,eq,g,gt} specifier.
+	const auto prefixes=set<string>(
+		{
+			"max",
+			"min",
+			"mov",
+			"movl",
+			"cmp",
+			"movh",
+			"add",
+			"sub",
+			"sqrt",
+			"mul",
+			"div",
+			"ucomi",
+			"cvtpi2",
+			"shuf",
+			//"cvtsi2",  had to remove this one?
+		});
+	const auto suffixes=set<string>(
+		{
+			"sd",
+			"ss",
+			"ps",
+			"pd"
+		});
+
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	auto full_str=getMnemonic()+" "+the_insn->op_str;
+
+	myReplace(full_str," ptr ", " ");
+	myReplace(full_str," xword ", " tword ");
+	myReplace(full_str," xmmword ", " ");
+
+
+	const auto has_prefix_it=find_if(ALLOF(prefixes),[&](const string& prefix) 
+		{ const auto s=getMnemonic(); return s.substr(0,prefix.size())==prefix; } );
+	const auto has_prefix = has_prefix_it != prefixes.end();
+	const auto has_suffix_it=find_if(ALLOF(suffixes),[&](const string& suffix) 
+		{ const auto s=getMnemonic(); return s.rfind(suffix) == (s.size() - suffix.size()); } );
+	const auto has_suffix = has_suffix_it != suffixes.end();
+
+	const auto needs_memdec_special=no_memdec_mnemonics.find(getMnemonic())==end(no_memdec_mnemonics);
+	const auto needs_memdec_shape=!(has_prefix && has_suffix);
+	const auto needs_memdec=needs_memdec_special && needs_memdec_shape;
+
+	//const auto no_dec1=needs_memdec ? noxmmword : (myReplace(noxmmword," qword ", " ")) ;
+	//const auto no_dec2=needs_memdec ? no_dec1 : (myReplace(no_dec1," dword ", " ")) ;
+	//const auto no_rip=myReplace(no_dec2, "rip", to_string(the_insn->size));
+
+	if(!needs_memdec) 
+	{
+		myReplace(full_str," qword ", " ");
+		myReplace(full_str," dword ", " ");
+	}
+
+	myReplace(full_str, "rip", to_string(the_insn->size));
+
+	return full_str;
+}
+
+bool DecodedInstructionCapstoneX86_t::valid() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return the_insn->size!=0;
+}
+
+uint32_t DecodedInstructionCapstoneX86_t::length() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return the_insn->size;
+}
+
+bool DecodedInstructionCapstoneX86_t::isBranch() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isCall() || isReturn() || isJmp(the_insn);
+}
+
+bool DecodedInstructionCapstoneX86_t::isCall() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isPartOfGroup(the_insn,X86_GRP_CALL);
+}
+
+bool DecodedInstructionCapstoneX86_t::isUnconditionalBranch() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	return isJmp(the_insn) && !isConditionalBranch();
+}
+
+bool DecodedInstructionCapstoneX86_t::isConditionalBranch() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isJmp(the_insn) && getMnemonic()!="jmp";
+}
+
+bool DecodedInstructionCapstoneX86_t::isReturn() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return isPartOfGroup(the_insn,X86_GRP_RET);
+}
+
+bool DecodedInstructionCapstoneX86_t::hasOperand(const int op_num) const
+{
+	if(op_num<0) throw std::logic_error(string("Called ")+ __FUNCTION__+" with opnum="+to_string(op_num));
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	const auto &x86 = (the_insn->detail->x86);
+	return 0 <= op_num  && op_num < x86.op_count;
+}
+
+// 0-based.  first operand is numbered 0.
+shared_ptr<DecodedOperand_t> DecodedInstructionCapstoneX86_t::getOperand(const int op_num) const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	if(!hasOperand(op_num)) throw std::logic_error(string("Called ")+__FUNCTION__+" on without hasOperand()==true");
+
+	return shared_ptr<DecodedOperand_t>(new DecodedOperandCapstoneX86_t(my_insn,(uint8_t)op_num));
+	
+}
+
+IRDB_SDK::DecodedOperandVector_t DecodedInstructionCapstoneX86_t::getOperands() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	const auto &x86 = (the_insn->detail->x86);
+	const auto opcount=x86.op_count;
+
+	auto ret_val=IRDB_SDK::DecodedOperandVector_t();
+	
+	for(auto i=0;i<opcount;i++)
+		ret_val.push_back(getOperand(i));
+
+	return ret_val;
+}
+
+string DecodedInstructionCapstoneX86_t::getMnemonic() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	// list of opcodes to rename capstone to bea engine names
+	typedef pair<string,string>  renamer_t; 
+	const auto renamer=set<renamer_t>(
+	{
+		/* bea (right), capstone */
+		{ "mov", "movabs" } ,
+ 		{ "fucomip", "fucompi" }, 
+ //		{ "cmovnb", "cmovae" }, 
+ //		{ "cmovnbe", "cmova" }, 
+ //		{ "cmovnle", "cmovg" }, 
+//		{ "jnbe", "ja"},
+//		{ "jnc", "jae"},
+//		{ "jng", "jle"},
+//		{ "jnl", "jge"},
+//		{ "jnle", "jg"},
+ //		{ "movsd", "movsd" }, 
+ //		{ "setnbe", "seta" }, 
+ //		{ "setnle", "setg" }, 
+
+	});
+
+	// get the cs insn via casting.
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	
+	// get mnemonic as a string
+	auto mnemonic=string(the_insn->mnemonic);
+
+
+	// remove any prefixes by finding the last space and removing anything before it.
+	const auto space_pos=mnemonic.rfind(" ");
+	if(space_pos!=string::npos)
+		mnemonic.erase(0,space_pos+1);
+		
+	// check if it needs a rename.
+	const auto finder_it=find_if(ALLOF(renamer), [&](const renamer_t& r) { return r.second==the_insn->mnemonic; } );
+	if(finder_it!=end(renamer)) 
+		mnemonic=finder_it->first;
+
+	// return the new string.
+	return mnemonic;
+
+	
+}
+
+
+int64_t DecodedInstructionCapstoneX86_t::getImmediate() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	// direct calls and jumps have a "immediate" which is really an address"  those are returned by getAddress
+	if(isCall() || isJmp(the_insn))
+		return 0;
+
+	return insnToImmedHelper<int64_t>(the_insn, cs_handle->getHandle());
+}
+
+
+virtual_offset_t DecodedInstructionCapstoneX86_t::getAddress() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	if(isCall() || isJmp(the_insn))
+		return insnToImmedHelper<virtual_offset_t>(the_insn, cs_handle->getHandle());
+
+
+        const auto count = cs_op_count(cs_handle->getHandle(), the_insn, X86_OP_MEM);
+	const auto x86 = &(the_insn->detail->x86);
+
+        if (count==0) 
+		return 0;	 /* no immediate is the same as an immediate of 0, i guess? */
+        else if (count==1) 
+	{
+		const auto index = cs_op_index(cs_handle->getHandle(), the_insn, X86_OP_MEM, 1);
+		if(x86->operands[index].mem.base==X86_REG_RIP)
+			return X86_REL_ADDR(*the_insn);
+		if(getMnemonic()=="lea")
+			return 0;
+		return x86->operands[index].mem.disp;
+	}
+	else
+		return 0;
+}
+
+
+bool DecodedInstructionCapstoneX86_t::setsStackPointer() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+/* slow string manip */
+        if(getMnemonic()=="push")
+                return true;
+        if(getMnemonic()=="pop")
+                return true;
+        if(getMnemonic()=="call")
+                return true;
+
+	// any sp reg
+	const auto sp_regs=set<x86_reg>({X86_REG_RSP, X86_REG_ESP, X86_REG_SP, X86_REG_SPL});
+
+	// check the implicit regs.
+	const auto regs_write_end=begin(the_insn->detail->regs_write)+the_insn->detail->regs_write_count;
+	const auto implicit_regs_it=find_if
+		(
+			begin(the_insn->detail->regs_write),
+			regs_write_end,
+			[sp_regs](const uint8_t actual_reg) 
+			{ 
+				return sp_regs.find((x86_reg)actual_reg)!=sp_regs.end();
+			} 
+		) ;
+	if(implicit_regs_it!=regs_write_end)	
+		return true;
+
+
+	// now check each operand
+	const auto operands_begin=begin(the_insn->detail->x86.operands);
+	const auto operands_end=begin(the_insn->detail->x86.operands)+the_insn->detail->x86.op_count;
+	const auto rsp_it=find_if
+		(
+			begin(the_insn->detail->x86.operands), 
+			operands_end,
+			[sp_regs](const cs_x86_op& op)
+			{
+				return op.type==X86_OP_REG && sp_regs.find(op.reg)!=sp_regs.end();
+			}
+		);
+	// not found in the operands, we're done.
+	if(rsp_it==operands_end)	
+	        return false;
+
+	// now decide if it's a register that's read or written.
+
+	// special check for things without a destation (as op[0])
+	if(getMnemonic()=="push" || 
+	   getMnemonic()=="cmp"  ||
+	   getMnemonic()=="call" ||
+	   getMnemonic()=="test")
+		return false;
+
+	// standard check -- is the reg op 0
+	const auto is_op0=(rsp_it==operands_begin);
+
+	return is_op0;
+}
+
+uint32_t DecodedInstructionCapstoneX86_t::getPrefixCount() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	const auto count=count_if(ALLOF(the_insn->detail->x86.prefix), [](const uint8_t pref) { return pref!=0x0; } ) ;
+	const auto count_with_rex = the_insn->detail->x86.rex == 0 ? count : count + 1;
+	return count_with_rex;
+}
+
+IRDB_SDK::VirtualOffset_t DecodedInstructionCapstoneX86_t::getMemoryDisplacementOffset(const IRDB_SDK::DecodedOperand_t* p_t, const IRDB_SDK::Instruction_t* insn) const
+{
+	auto &t = *p_t;
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+	//const auto encoding_size=t.getMemoryDisplacementEncodingSize();
+	//const auto x86 = &(the_insn->detail->x86);
+    const auto imm_count = cs_op_count(cs_handle->getHandle(), the_insn, X86_OP_IMM);
+	const auto disp_size=t.getMemoryDisplacementEncodingSize();
+	const auto imm=getImmediate();
+	const auto disp=t.getMemoryDisplacement();
+
+	if(string((char*)the_insn->detail->x86.opcode)=="\x0f\xc2") // CMPPD, CMPSS 
+	{
+		return the_insn->size - disp_size - 1;  // last byte encodes an immediate value to distinguish pseudo-ops
+	}
+	
+	if(imm_count==0)
+		return the_insn->size - disp_size;
+
+	// shifts can an immediate that's note encoded in the instruction
+	// but never an immediate encoded in the instruction.
+	if(
+	   string((char*)the_insn->detail->x86.opcode)=="\xd0" || // shift left or right with an immediate that's not actually  encoded in the insn
+	   string((char*)the_insn->detail->x86.opcode)=="\xd1" 
+	  )
+		return the_insn->size - disp_size;
+
+	const auto possible_imm_sizes= string(the_insn->mnemonic)=="movabs" ?  set<int>({1,2,4,8}) : set<int>({1,2,4});
+
+	// Reverse iterate to find the maximum size value-match possible.
+	//  E.g. with a mov [rbx*8 + 0x00000000],0x00000000 instruction, it would be easy to match
+	//  a 1-byte immediate value of 0 and a 4-byte displacement value of zero, while
+	//  the desired behavior is to match two 4-byte values of zero when searching
+	//  for the actual start offsets of the displacement and immediate fields.
+	for (auto imm_size_iter = possible_imm_sizes.crbegin(); imm_size_iter != possible_imm_sizes.crend(); ++imm_size_iter)
+	{
+		const auto imm_size = (*imm_size_iter);
+		if(the_insn->size < disp_size + imm_size)
+			continue;
+
+		const auto disp_start=the_insn->size-imm_size-disp_size;
+		const auto imm_start=the_insn->size-imm_size;
+		
+		const auto candidate_disp_eq = disp_size==4  ? *(int32_t*)(&insn->getDataBits().c_str()[disp_start])==(int32_t)disp :
+		                               disp_size==2  ? *(int16_t*)(&insn->getDataBits().c_str()[disp_start])==(int16_t)disp :
+		                               disp_size==1  ? *(int8_t *)(&insn->getDataBits().c_str()[disp_start])==(int8_t )disp : (assert(0),false);
+
+		const auto candidate_imm_eq = imm_size==8  ? *(int64_t*)(&insn->getDataBits().c_str()[imm_start])==(int64_t)imm :
+					      imm_size==4  ? *(int32_t*)(&insn->getDataBits().c_str()[imm_start])==(int32_t)imm :
+					      imm_size==2  ? *(int16_t*)(&insn->getDataBits().c_str()[imm_start])==(int16_t)imm :
+		                              imm_size==1  ? *(int8_t *)(&insn->getDataBits().c_str()[imm_start])==(int8_t )imm : (int64_t)(assert(0),false);
+
+		if(candidate_disp_eq && candidate_imm_eq)
+			return disp_start;
+		
+	}
+
+	assert(0);
+
+
+}
+
+
+
+bool DecodedInstructionCapstoneX86_t::hasRelevantRepPrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return hasPrefix(the_insn,X86_PREFIX_REP);
+}
+
+bool DecodedInstructionCapstoneX86_t::hasRelevantRepnePrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return hasPrefix(the_insn,X86_PREFIX_REPNE);
+}
+
+bool DecodedInstructionCapstoneX86_t::hasRelevantOperandSizePrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return hasPrefix(the_insn,X86_PREFIX_OPSIZE);
+}
+
+bool DecodedInstructionCapstoneX86_t::hasRexWPrefix() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+	return (the_insn->detail->x86.rex & 0x8) == 0x8;
+}
+
+bool DecodedInstructionCapstoneX86_t::hasImplicitlyModifiedRegs() const
+{
+	if(!valid()) throw std::logic_error(string("Called ")+__FUNCTION__+" on invalid instruction");
+
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+
+
+	const auto count=count_if
+		(
+			begin(the_insn->detail->regs_write),
+			begin(the_insn->detail->regs_write)+the_insn->detail->regs_write_count,
+			[](const uint8_t actual_pref) 
+			{ 
+				return actual_pref!=X86_REG_EFLAGS; 
+			} 
+		) ;
+	
+	return count>0;
+
+}
+
diff --git a/irdb-lib/libIRDB-core/src/decode_dispatch.cpp b/irdb-lib/libIRDB-core/src/decode_dispatch.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..97631d5cbad1dacf76a3a569b157251ee08f4c68
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/decode_dispatch.cpp
@@ -0,0 +1,115 @@
+
+#include <libIRDB-core.hpp>
+#include <decode_base.hpp>
+#include <decode_csx86.hpp>
+#include <decode_csarm.hpp>
+
+#include <operand_base.hpp>
+#include <operand_csx86.hpp>
+#include <operand_csarm.hpp>
+
+#include <decode_dispatch.hpp>
+#include <operand_dispatch.hpp>
+
+
+using namespace libIRDB;
+using namespace std;
+
+// constructors, destructors, operators.
+
+DecodedInstructionDispatcher_t::DecodedInstructionDispatcher_t(const Instruction_t* i) 
+{
+	cs=DecodedInstructionCapstone_t::factory(i);
+}
+
+DecodedInstructionDispatcher_t::DecodedInstructionDispatcher_t(const virtual_offset_t start_addr, const void *data, uint32_t max_len) 
+{
+	cs=DecodedInstructionCapstone_t::factory(start_addr,data,max_len);
+}
+
+DecodedInstructionDispatcher_t::DecodedInstructionDispatcher_t(const virtual_offset_t start_addr, const void *data, const void* endptr) 
+{
+	cs=DecodedInstructionCapstone_t::factory(start_addr,data,endptr);
+}
+
+DecodedInstructionDispatcher_t::DecodedInstructionDispatcher_t(const DecodedInstructionDispatcher_t& copy) 
+{
+	cs=copy.cs; 
+}
+
+DecodedInstructionDispatcher_t::~DecodedInstructionDispatcher_t()
+{
+}
+
+DecodedInstructionDispatcher_t& DecodedInstructionDispatcher_t::operator=(const DecodedInstructionDispatcher_t& copy)
+{
+	cs=copy.cs; 
+	return *this;
+}
+
+
+
+#define passthrough_to_cs(ret_type, method_name) 						\
+	ret_type DecodedInstructionDispatcher_t::method_name() const 				\
+	{ 											\
+		return cs->method_name(); 							\
+	} 
+
+// public methods
+
+/* demonstrating things are the same */
+passthrough_to_cs(bool, valid);
+passthrough_to_cs(uint32_t, length);
+passthrough_to_cs(bool, isBranch);
+passthrough_to_cs(bool, isCall);
+passthrough_to_cs(bool, isUnconditionalBranch);
+passthrough_to_cs(bool, isConditionalBranch);
+passthrough_to_cs(bool, isReturn);
+passthrough_to_cs(uint32_t, getPrefixCount);
+passthrough_to_cs(bool, hasRexWPrefix);
+passthrough_to_cs(bool, setsStackPointer);
+passthrough_to_cs(bool, hasRelevantRepPrefix);		// rep ret disagreement.
+passthrough_to_cs(bool, hasRelevantRepnePrefix);
+passthrough_to_cs(bool, hasRelevantOperandSizePrefix);
+
+/* demonstrating when capstone is better */
+passthrough_to_cs(string, getMnemonic);
+passthrough_to_cs(string,getDisassembly);
+passthrough_to_cs(virtual_offset_t, getAddress);	 
+passthrough_to_cs(int64_t, getImmediate);
+
+// demonstrating they different and trying to determine which is better.
+passthrough_to_cs(bool, hasImplicitlyModifiedRegs); 	
+
+// not yet completed
+// needs more complicated impl.
+
+
+bool DecodedInstructionDispatcher_t::hasOperand(const int op_num) const
+{
+	const auto cs_res = cs->hasOperand(op_num);
+	return cs_res; 									
+}
+
+// 0-based.  first operand is numbered 0.
+unique_ptr<DecodedOperand_t> DecodedInstructionDispatcher_t::getOperand(const int op_num) const
+{
+	return unique_ptr<DecodedOperand_t>(new DecodedOperandDispatcher_t(cs->getOperand(op_num)));
+}
+
+DecodedOperandMetaVector_t DecodedInstructionDispatcher_t::getOperands() const
+{
+	auto ret_val=DecodedOperandMetaVector_t();
+	auto cs_operands=cs->getOperands();
+	for(const auto &op : cs_operands ) 
+		ret_val.push_back(DecodedOperandDispatcher_t(op));
+	return ret_val;
+}
+
+virtual_offset_t DecodedInstructionDispatcher_t::getMemoryDisplacementOffset(const DecodedOperandDispatcher_t& t, const Instruction_t* insn) const
+{
+	return cs->getMemoryDisplacementOffset(*t.cs, insn);
+}
+
+
+
diff --git a/irdb-lib/libIRDB-core/src/eh.cpp b/irdb-lib/libIRDB-core/src/eh.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..fea5ca337dbd240bac597e77a55383a0a40cfcd3
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/eh.cpp
@@ -0,0 +1,163 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <all.hpp>
+#include <irdb-util>
+#include <tuple>
+#include <functional>
+#include <assert.h>
+#include <sstream>
+#include <iostream>
+#include <iomanip>
+#include <algorithm>
+
+using namespace libIRDB;
+using namespace std;
+
+bool libIRDB::operator<(const EhProgram_t&a, const EhProgram_t&b)
+{
+        return  tie(a.cie_program,a.fde_program,a.code_alignment_factor,a.data_alignment_factor,a.return_register, a.ptrsize, a.getRelocations())
+                <
+                tie(b.cie_program,b.fde_program,b.code_alignment_factor,b.data_alignment_factor,b.return_register, b.ptrsize, b.getRelocations());
+}
+
+namespace std
+{
+template<>
+class hash<EhProgramListing_t> 
+{
+	public:
+		std::size_t operator()(const EhProgramListing_t& s) const
+		{
+			auto sub_hasher=std::hash<string>();
+			auto res=std::size_t(0);
+			for(const auto& i: s)
+			{
+				res ^= sub_hasher(i);
+			}
+			return res;
+		}
+	
+};
+}
+
+
+void libIRDB::EhProgram_t::print() const
+{
+	std::hash<EhProgramListing_t> ehpgmlist_hash;
+	auto cie_hash=ehpgmlist_hash(cie_program);
+	auto fde_hash=ehpgmlist_hash(fde_program);
+	cout<<dec<<"CAF: "<<code_alignment_factor<<" DAF: "<<data_alignment_factor<<" ptrsize="<< +ptrsize<<" cie_hash: "<<hex<<cie_hash<<" fde_hash: "<<fde_hash<<endl;
+}
+
+vector<std::string> EhProgram_t::WriteToDB(File_t* fid)    // writes to DB, ID is not -1.
+{
+	auto str_to_encoded_string=[](const string& data) -> string
+	{
+		ostringstream hex_data;
+		hex_data << setfill('0') << hex;
+		for (size_t i = 0; i < data.length(); ++i)
+			hex_data << setw(2) << (int)(data[i]&0xff);
+		return hex_data.str();
+	};
+
+	auto vec_to_encoded_string=[&](const vector<string>& in) -> string
+	{
+		string q="";
+		for(const auto& i : in)
+		{
+			if(q!="") 	
+				q+=",";
+			q+=str_to_encoded_string(i);	
+		}
+		return q;
+	};
+
+	string encoded_cie_program=vec_to_encoded_string(cie_program);
+	string encoded_fde_program=vec_to_encoded_string(fde_program);
+
+
+	return {
+		to_string(getBaseID()),
+		to_string(+code_alignment_factor),
+		to_string(+data_alignment_factor),
+		to_string(+return_register),
+		to_string(+ptrsize),
+		encoded_cie_program,
+		encoded_fde_program
+		};
+
+}
+
+std::string EhCallSite_t::WriteToDB(File_t* fid)    // writes to DB, ID is not -1.
+{
+	const auto vec_to_string=[](const vector<int> &v)
+	{
+		stringstream s;
+		for(const auto &e : v)
+		{
+			s<<dec<<e<<" ";
+		}
+		
+		return s.str();
+	};
+	string q;
+
+	
+
+	auto landing_pad_id=BaseObj_t::NOT_IN_DATABASE;
+	if(landing_pad != NULL)
+		landing_pad_id=landing_pad->getBaseID();
+
+	const auto ttov_str=vec_to_string(ttov);
+
+	q ="insert into " + fid->getEhCallSiteTableName();
+	q+="(ehcs_id,tt_encoding,ttov,lp_insn_id) "+
+		string(" VALUES (") +
+		string("'") + to_string(getBaseID())         + string("', ") +
+		string("'") + to_string(+tt_encoding)        + string("', ") +
+		string("'") + ttov_str        + string("', ") +
+		string("'") + to_string(landing_pad_id)      + string("') ;");
+	return q;
+}
+
+bool EhCallSite_t::getHasCleanup() const 
+{
+	const auto ttov_it=find(ttov.begin(), ttov.end(), 0);
+	return ttov_it!=ttov.end();
+}
+
+void EhCallSite_t::setHasCleanup(bool p_has_cleanup) 
+{
+	if(p_has_cleanup)
+	{
+		if(!getHasCleanup())
+			ttov.push_back(0);
+	}
+	else
+	{
+		if(getHasCleanup())
+		{
+			const auto ttov_it=find(ttov.begin(), ttov.end(), 0);
+			ttov.erase(ttov_it);
+		}
+	}
+}
+
diff --git a/irdb-lib/libIRDB-core/src/file.cpp b/irdb-lib/libIRDB-core/src/file.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..87a55124bb4324f7d4859786c08ce2e1256cf363
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/file.cpp
@@ -0,0 +1,95 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <all.hpp>
+#include <irdb-util>
+#include <stdlib.h>
+#include <unistd.h>
+#include <fstream>
+#include <iostream>
+
+#include <irdb-util>
+
+using namespace libIRDB;
+using namespace std;
+
+
+File_t::File_t(const db_id_t &myfile_id, const db_id_t &my_orig_fid, const std::string &myurl, 
+	       const std::string &myhash, const std::string &myarch, const int &myoid, 
+	       const std::string &atn, const std::string &ftn, const std::string &itn, const std::string &icfs, 
+               const std::string &icfs_map, const std::string &rtn, const std::string &typ, const std::string &scoop, 
+               const std::string &ehpgms, const std::string &ehcss, 
+	       const db_id_t &mydoipid) 
+	:
+	BaseObj_t(NULL), 
+	orig_fid(my_orig_fid),
+	url(myurl), 
+	hash(myhash), 
+	arch(myarch), 
+	address_table_name(atn), 
+	function_table_name(ftn), 
+	instruction_table_name(itn), 
+  	icfs_table_name(icfs), 
+	icfs_map_table_name(icfs_map), 
+	relocs_table_name(rtn), 
+	types_table_name(typ), 
+	scoop_table_name(scoop), 
+	ehpgm_table_name(ehpgms), 
+	ehcss_table_name(ehcss), 
+	elfoid(myoid)
+{
+	setBaseID(myfile_id);
+}
+
+
+void File_t::CreateTables()
+{
+
+	// to avoid duplicate schemas for the DB, we're calling 
+	// the script that has the table creation schema in it  
+	string home(getenv("PEASOUP_HOME"));
+	string tmpfile= "db_script."+to_string(getpid());
+
+	string command=home+"/tools/db/pdb_create_program_tables.sh "+
+		address_table_name+" "+
+		function_table_name+" "+
+		instruction_table_name+" "+
+		icfs_table_name+" "+
+		icfs_map_table_name+" "+
+		relocs_table_name+" "+
+		types_table_name+" "+
+		scoop_table_name+" "+
+		ehpgm_table_name+" "+
+		ehcss_table_name+" "+
+		tmpfile;
+
+	// ignore_result(system(command.c_str()));
+	command_to_stream(command,cout);
+
+
+	std::ifstream t(tmpfile.c_str());
+	std::stringstream buffer;
+	buffer << t.rdbuf();
+
+
+	dbintr->issueQuery(buffer.str().c_str());	
+
+}
diff --git a/irdb-lib/libIRDB-core/src/fileir.cpp b/irdb-lib/libIRDB-core/src/fileir.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..14502548e6d95423ff93e52ecd9b2a9c28e7bce9
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/fileir.cpp
@@ -0,0 +1,1919 @@
+
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <all.hpp>
+#include <irdb-util>
+#include <cstdlib>
+#include <map>
+#include <fstream>
+#include <elf.h>
+#include <stdlib.h>
+#include <algorithm>
+#include <sys/wait.h>
+#include <iomanip>
+#include <irdb-util>
+
+using namespace libIRDB;
+using namespace std;
+
+
+#define SCOOP_CHUNK_SIZE (10*1024*1024)  /* 10 mb  */
+#define ALLOF(a) begin(a),end(a)
+
+
+#undef EIP
+
+int command_to_stream(const string& command, ostream& stream)
+{
+	auto redirect_command=command+" 2>&1 ";
+	auto buffer=array<char,128>();
+
+	std::cout << "Issuing subcommand: "<< command << std::endl;
+	auto pipe = popen(redirect_command.c_str(), "r");
+	if (!pipe)
+	{
+		stream << "Couldn't start command:"<< strerror(errno) << endl;
+		return 1;
+	}
+	while (fgets(buffer.data(), 128, pipe) != NULL) 
+	{
+		stream<<buffer.data();
+	}
+	auto returnCode = pclose(pipe);
+	if(returnCode==-1)
+		stream << "Could not close pipe: "<< strerror(errno) << endl;
+
+	std::cout << "Return code = "<<returnCode << std::endl;
+	return returnCode;
+}
+
+static void UpdateEntryPoints(
+	const std::map<db_id_t,Instruction_t*> 	&insnMap,
+	const map<Function_t*,db_id_t>& entry_points)
+{
+	/* for each function, look up the instruction that's the entry point */
+	for(	map<Function_t*,db_id_t>::const_iterator it=entry_points.begin();
+		it!=entry_points.end();
+		++it
+	   )
+	{
+		Function_t* func=(*it).first;
+		db_id_t func_entry_id=(*it).second;
+
+		assert(func_entry_id==-1 || insnMap.at(func_entry_id));
+		func->setEntryPoint(insnMap.at(func_entry_id));
+//		cout<<"Function named "<<func->getName()<< " getting entry point set to "<<insnMap[func_entry_id]->getComment()<<"."<<endl;
+	}
+		
+}
+
+static void UpdateUnresolvedEhCallSites(
+	const std::map<db_id_t,Instruction_t*> 	&insnMap,
+	const std::map<EhCallSite_t*,db_id_t> & unresolvedEhcss)
+{
+	for(const auto &i : unresolvedEhcss)
+	{
+		const auto& ehcs=i.first; 
+		const auto& insnid=i.second;
+		const auto& insn=insnMap.at(insnid);
+		assert(insn);
+		ehcs->setLandingPad(insn);
+	}
+}
+
+static virtual_offset_t strtovo(std::string s)
+{
+        return IRDB_SDK::strtoint<virtual_offset_t>(s);
+}
+
+// Create a Variant from the database
+FileIR_t::FileIR_t(const VariantID_t &newprogid, File_t* fid) 
+			: BaseObj_t(NULL), progid((VariantID_t&) newprogid)
+	
+{
+	orig_variant_ir_p=NULL;
+
+	if(fid==NULL)
+		fileptr=dynamic_cast<File_t*>(newprogid.getMainFile());
+	else
+		fileptr=fid;
+
+	if(progid.isRegistered())
+	{
+		ReadFromDB();
+		setArchitecture();
+	}
+
+}
+
+FileIR_t::~FileIR_t()
+{
+	for(auto i : funcs ) delete i;
+	for(auto i : insns ) delete i;
+	for(auto i : addrs ) delete i;
+	for(auto i : relocs) delete i;
+	for(auto i : types ) delete i;
+
+	// @todo: clear icfs_t
+}
+  
+// DB operations
+void FileIR_t::ReadFromDB()
+{
+    	ReadIRDB_start = clock();
+
+
+	auto entry_points=map<Function_t*,db_id_t>();
+	auto unresolvedICFS=std::map<Instruction_t*, db_id_t>();
+	auto unresolvedEhCallSites=std::map<EhCallSite_t*,db_id_t>();
+	auto objMap=std::map<db_id_t,BaseObj_t*>();
+	auto addressToInstructionMap=std::map<db_id_t,Instruction_t*>();
+
+	auto ehpgmMap 	= ReadEhPgmsFromDB(); 
+	auto ehcsMap 	= ReadEhCallSitesFromDB(unresolvedEhCallSites); 
+	auto typesMap 	= ReadTypesFromDB(types); 
+	auto addrMap	= ReadAddrsFromDB();
+	auto funcMap	= ReadFuncsFromDB(addrMap, typesMap,entry_points);
+	auto scoopMap	= ReadScoopsFromDB(addrMap, typesMap);
+	auto insnMap	= ReadInsnsFromDB(funcMap,addrMap,ehpgmMap,ehcsMap,addressToInstructionMap, unresolvedICFS);
+
+
+	ReadAllICFSFromDB(addressToInstructionMap, unresolvedICFS);
+
+	// put the scoops, instructions, ehpgms, eh call sites into the object map.
+	// if relocs end up on other objects, we'll need to add them to.  for now only these things.
+	objMap.insert(insnMap.begin(), insnMap.end());
+	objMap.insert(scoopMap.begin(), scoopMap.end());
+	objMap.insert(ehcsMap.begin(), ehcsMap.end());
+	objMap.insert(ehpgmMap.begin(), ehpgmMap.end());
+	ReadRelocsFromDB(objMap);
+
+	UpdateEntryPoints(insnMap,entry_points);
+	UpdateUnresolvedEhCallSites(insnMap,unresolvedEhCallSites);
+
+	ReadIRDB_end = clock();
+
+
+}
+
+
+void  FileIR_t::changeRegistryKey(IRDB_SDK::Instruction_t *p_orig, IRDB_SDK::Instruction_t *p_updated)
+{
+	auto orig=dynamic_cast<libIRDB::Instruction_t*>(p_orig);
+	auto updated=dynamic_cast<libIRDB::Instruction_t*>(p_updated);
+
+	if(assembly_registry.find(orig) != assembly_registry.end())
+	{
+		assembly_registry[updated] = assembly_registry[orig];
+
+		assembly_registry.erase(orig);
+	}
+}
+
+void FileIR_t::assembleRegistry()
+{
+	if(assembly_registry.size() == 0)
+		return;
+
+	string assemblyFile = "tmp.asm";
+	string binaryOutputFile = "tmp.bin";
+
+	string command = "rm -f " + assemblyFile + " " + binaryOutputFile;
+	auto actual_exit = command_to_stream(command, cout); // system(command.c_str());
+	
+	assert(actual_exit == 0);
+	
+	ofstream asmFile;
+	asmFile.open(assemblyFile.c_str());
+	if(!asmFile.is_open())
+		assert(false);
+
+	asmFile<<"BITS "<<std::dec<<getArchitectureBitWidth()<<endl; 
+
+	for(auto it : assembly_registry)
+	{
+		asmFile<<it.second<<endl;
+	}
+	asmFile.close();
+
+	command = string("nasm ") + assemblyFile + string(" -o ") + binaryOutputFile;
+	actual_exit = command_to_stream(command,cout); // system(command.c_str());
+	assert(actual_exit == 0);
+	
+	ifstream binreader;
+	unsigned int filesize;
+	binreader.open(binaryOutputFile.c_str(),ifstream::in|ifstream::binary);
+
+	assert(binreader.is_open());
+
+	binreader.seekg(0,ios::end);
+	filesize = binreader.tellg();
+	binreader.seekg(0,ios::beg);
+
+	unsigned char *binary_stream = new unsigned char[filesize];
+
+	binreader.read((char*)binary_stream,filesize);
+	binreader.close();
+
+	unsigned int index = 0;
+	registry_type::iterator reg_val =  assembly_registry.begin();
+
+	while(index < filesize)
+	{
+		//the number of registered instructions should not be exceeded
+		assert(reg_val != assembly_registry.end());
+		Instruction_t *instr = reg_val->first;
+
+
+		// disasm.EIP =  (UIntPtr)&binary_stream[index];
+		// int instr_len = Disasm(&disasm);
+
+		const auto p_disasm=DecodedInstruction_t::factory
+			(
+				/* fake start addr doesn't matter */0x1000, 
+				(void*)&binary_stream[index], 
+				(void*)&binary_stream[filesize]
+			);
+		const auto& disasm=*p_disasm;
+
+		assert(disasm.valid());
+		const auto instr_len=disasm.length();
+
+		string rawBits;
+		rawBits.resize(instr_len);
+		for(auto i=0U;i<instr_len;i++,index++)
+		{
+			rawBits[i] = binary_stream[index];
+		}
+
+		instr->setDataBits(rawBits);
+//		*verbose_logging << "doing instruction:" << ((Instruction_t*)instr)->getDisassembly() << " comment: " << ((Instruction_t*)instr)->getComment() << endl;
+		reg_val++;
+	}
+
+	assert(reg_val == assembly_registry.end());
+
+	delete [] binary_stream;
+	assembly_registry.clear();
+
+}
+
+void FileIR_t::registerAssembly(IRDB_SDK::Instruction_t *p_instr, string assembly)
+{
+	auto instr=dynamic_cast<Instruction_t*>(p_instr);
+	assert(instr);
+	assembly_registry[instr] = assembly;
+}
+
+void FileIR_t::unregisterAssembly(IRDB_SDK::Instruction_t *p_instr)
+{
+	auto instr=dynamic_cast<Instruction_t*>(p_instr);
+	assert(instr);
+	assembly_registry.erase(instr);
+}
+
+std::string FileIR_t::lookupAssembly(IRDB_SDK::Instruction_t *p_instr)
+{
+	auto instr=dynamic_cast<Instruction_t*>(p_instr);
+	assert(instr);
+	if (assembly_registry.find(instr) != assembly_registry.end())
+		return assembly_registry[instr];
+	else
+		return std::string();
+}
+
+std::map<db_id_t,Function_t*> FileIR_t::ReadFuncsFromDB
+	(
+        	std::map<db_id_t,AddressID_t*> &addrMap,
+		std::map<db_id_t,Type_t*> &typesMap,
+		map<Function_t*,db_id_t> &entry_points
+	)
+{
+	auto idMap=std::map<db_id_t,Function_t*> ();
+
+	auto q=std::string("select * from ") + fileptr->function_table_name + " ; ";
+
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+// function_id | file_id | name | stack_frame_size | out_args_region_size | use_frame_pointer | is_safe | doip_id
+
+		db_id_t fid=atoi(dbintr->getResultColumn("function_id").c_str());
+		db_id_t entry_point_id=atoi(dbintr->getResultColumn("entry_point_id").c_str());
+		std::string name=dbintr->getResultColumn("name");
+		int sfsize=atoi(dbintr->getResultColumn("stack_frame_size").c_str());
+		int oasize=atoi(dbintr->getResultColumn("out_args_region_size").c_str());
+		db_id_t function_type_id=atoi(dbintr->getResultColumn("type_id").c_str());
+// postgresql encoding of boolean can be 'true', '1', 'T', 'y'
+		bool useFP=false;
+		bool isSafe=false;
+		string useFPString=dbintr->getResultColumn("use_frame_pointer"); 
+		string isSafeString=dbintr->getResultColumn("is_safe"); 
+		const char *useFPstr=useFPString.c_str();
+		const char *isSafestr=isSafeString.c_str();
+		if (strlen(useFPstr) > 0)
+		{
+			if (useFPstr[0] == 't' || useFPstr[0] == 'T' || useFPstr[0] == '1' || useFPstr[0] == 'y' || useFPstr[0] == 'Y')
+				useFP = true;
+		}
+
+		if (strlen(isSafestr) > 0)
+		{
+			if (isSafestr[0] == 't' || isSafestr[0] == 'T' || isSafestr[0] == '1' || isSafestr[0] == 'y' || isSafestr[0] == 'Y')
+				isSafe = true;
+		}
+
+		// handle later?
+		//db_id_t doipid=atoi(dbintr->getResultColumn("doip_id").c_str());
+
+		FuncType_t* fnType = NULL;
+		if (typesMap.count(function_type_id) > 0)
+			fnType = dynamic_cast<FuncType_t*>(typesMap[function_type_id]);
+		Function_t *newfunc=new Function_t(fid,name,sfsize,oasize,useFP,isSafe,fnType, NULL); 
+		assert(newfunc);
+		entry_points[newfunc]=entry_point_id;
+		
+//std::cout<<"Found function "<<name<<"."<<std::endl;
+
+		idMap[fid]=newfunc;
+
+		funcs.insert(newfunc);
+
+		dbintr->moveToNextRow();
+	}
+
+	return idMap;
+}
+
+
+std::map<db_id_t,EhCallSite_t*> FileIR_t::ReadEhCallSitesFromDB
+	(
+		map<EhCallSite_t*,db_id_t> &unresolvedEhCssLandingPads // output arg.
+	)
+{
+	auto ehcsMap=std::map<db_id_t,EhCallSite_t*>();
+
+	std::string q= "select * from " + fileptr->getEhCallSiteTableName() + " ; ";
+
+	for(dbintr->issueQuery(q); !dbintr->isDone(); dbintr->moveToNextRow())
+	{
+		const auto string_to_vec=[&](const string& str ) ->  vector<int>
+		{
+			auto out=vector<int>();
+			istringstream s(str);
+			auto in=(int)0;
+			while ( s >> in)
+				out.push_back(in);
+			return out;
+		};
+		/* 
+		 * ehcs_id         integer,        -- id of this object.
+		 * tt_encoding     integer,        -- the encoding of the type table.
+		 * lp_insn_id      integer         -- the landing pad instruction's id.
+		 */
+
+
+		const auto eh_cs_id=atoi(dbintr->getResultColumn("ehcs_id").c_str());
+		const auto tt_encoding=atoi(dbintr->getResultColumn("tt_encoding").c_str());
+		const auto &ttov=string(dbintr->getResultColumn("ttov").c_str());
+		const auto lp_insn_id=atoi(dbintr->getResultColumn("lp_insn_id").c_str());
+
+		auto newEhCs=new EhCallSite_t(eh_cs_id,tt_encoding,NULL); // create the call site with an unresolved LP
+		newEhCs->GetTTOrderVector()=string_to_vec(ttov);
+		eh_css.insert(newEhCs);					  // record that it exists.
+		ehcsMap[eh_cs_id]=newEhCs;				  // record the map for when we read instructions.
+		if(lp_insn_id != BaseObj_t::NOT_IN_DATABASE)
+			unresolvedEhCssLandingPads[newEhCs]=lp_insn_id;		  // note that the LP is unresolved
+	}
+
+	return ehcsMap;
+}
+
+std::map<db_id_t,EhProgram_t*> FileIR_t::ReadEhPgmsFromDB()
+{
+	auto idMap = std::map<db_id_t,EhProgram_t*>();
+
+	auto q=std::string("select * from ") + fileptr->ehpgm_table_name + " ; ";
+	dbintr->issueQuery(q);
+
+	auto decode_pgm=[](const string& encoded_pgm, EhProgramListing_t& decoded_pgm)
+	{
+
+		auto split=[](const string& str, const string& delim, EhProgramListing_t& tokens) -> void
+		{
+			auto prev = size_t(0);
+			auto pos = size_t(0);
+			do
+			{
+				pos = str.find(delim, prev);
+				if (pos == string::npos) pos = str.length();
+				string token = str.substr(prev, pos-prev);
+				if (!token.empty()) tokens.push_back(token);
+				prev = pos + delim.length();
+			}
+			while (pos < str.length() && prev < str.length());
+		};
+
+		auto decode_in_place=[](string& to_decode) -> void
+		{
+			auto charToHex=[](uint8_t value) -> uint8_t
+			{
+				if (value >= '0' && value <= '9') return value - '0';
+				else if (value >= 'A' && value <= 'F') return value - 'A' + 10;
+				else if (value >= 'a' && value <= 'f') return value - 'a' + 10;
+				assert(false);
+			};
+
+
+			auto out=string("");
+			while(to_decode.size() > 0)
+			{
+				// to-decode should have pairs of characters that represent individual bytes.
+				assert(to_decode.size() >= 2);
+				auto val =  uint8_t ( charToHex(to_decode[0])*16  + charToHex(to_decode[1]) ); 
+				out += val;
+				to_decode.erase(0,2);
+			}
+
+			to_decode=out;
+		};
+
+		split(encoded_pgm, ",", decoded_pgm);
+
+		// decode each one
+		for(auto& i : decoded_pgm)
+			decode_in_place(i);
+		
+		
+	};
+
+	while(!dbintr->isDone())
+	{
+		/* 
+		 * eh_pgm_id       integer,
+		 * caf             integer,
+		 * daf             integer,
+		 * ptrsize         integer,
+		 * cie_program     text,
+		 * fde_program     text
+		 */
+
+
+		const auto eh_pgm_id=atoi(dbintr->getResultColumn("eh_pgm_id").c_str());
+		const auto caf=atoi(dbintr->getResultColumn("caf").c_str());
+		const auto daf=atoi(dbintr->getResultColumn("daf").c_str());
+		const auto rr=atoi(dbintr->getResultColumn("return_register").c_str());
+		const auto ptrsize=atoi(dbintr->getResultColumn("ptrsize").c_str());
+		const auto& encoded_cie_program = dbintr->getResultColumn("cie_program");
+		const auto& encoded_fde_program = dbintr->getResultColumn("fde_program");
+
+		auto new_ehpgm=new EhProgram_t(eh_pgm_id, caf, daf, rr, ptrsize, {}, {});
+		decode_pgm(encoded_cie_program, new_ehpgm->GetCIEProgram());
+		decode_pgm(encoded_fde_program, new_ehpgm->GetFDEProgram());
+
+		idMap[eh_pgm_id]=new_ehpgm;
+		eh_pgms.insert(new_ehpgm);
+		dbintr->moveToNextRow();
+	}
+
+	return idMap;
+}
+
+std::map<db_id_t,AddressID_t*> FileIR_t::ReadAddrsFromDB  
+	(
+	) 
+{
+	std::map<db_id_t,AddressID_t*> idMap;
+
+	std::string q= "select * from " + fileptr->address_table_name + " ; ";
+
+
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+//   address_id            integer PRIMARY KEY,
+//  file_id               integer REFERENCES file_info,
+//  vaddress_offset       bigint,
+//  doip_id               integer DEFAULT -1
+
+
+		db_id_t aid=atoi(dbintr->getResultColumn("address_id").c_str());
+		db_id_t file_id=atoi(dbintr->getResultColumn("file_id").c_str());
+		virtual_offset_t vaddr=strtovo(dbintr->getResultColumn("vaddress_offset"));
+
+		// handle later?
+		//db_id_t doipid=atoi(dbintr->getResultColumn("doip_id").c_str());
+
+		AddressID_t *newaddr=new AddressID_t(aid,file_id,vaddr);
+
+//std::cout<<"Found address "<<aid<<"."<<std::endl;
+
+		idMap[aid]=newaddr;
+
+		addrs.insert(newaddr);
+
+		dbintr->moveToNextRow();
+	}
+
+	return idMap;
+}
+
+
+static string encoded_to_raw_string(string encoded)
+{
+	int len = encoded.length();
+	std::string raw;
+	for(int i=0; i< len; i+=2)
+	{
+	    string byte = encoded.substr(i,2);
+	    char chr = (char) (int)strtol(byte.c_str(), nullptr, 16);
+	    raw.push_back(chr);
+	}
+	return raw;
+}
+
+std::map<db_id_t,Instruction_t*> FileIR_t::ReadInsnsFromDB 
+	(      
+        const std::map<db_id_t,Function_t*> &funcMap,
+        const std::map<db_id_t,AddressID_t*> &addrMap,
+        const std::map<db_id_t,EhProgram_t*> &ehpgmMap,
+        const std::map<db_id_t,EhCallSite_t*> &ehcsMap,
+	std::map<db_id_t,Instruction_t*> &addressToInstructionMap,
+	std::map<Instruction_t*, db_id_t> &unresolvedICFS
+        ) 
+{
+	std::map<db_id_t,Instruction_t*> idMap;
+	std::map<db_id_t,db_id_t> fallthroughs;
+	std::map<db_id_t,db_id_t> targets;
+
+	std::string q= "select * from " + fileptr->instruction_table_name + " ; ";
+
+
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+
+//  address_id                integer REFERENCES #PROGNAME#_address,
+//  parent_function_id        integer,
+//  orig_address_id           integer REFERENCES #PROGNAME#_address,
+//  fallthrough_address_id    integer,
+//  target_address_id         integer,
+//  icfs_id                   integer,
+//  data                      bytea,
+//  callback                  text,
+//  comment                   text,
+//  doip_id                   integer DEFAULT -1
+
+
+		db_id_t instruction_id=atoi(dbintr->getResultColumn("instruction_id").c_str());
+		db_id_t aid=atoi(dbintr->getResultColumn("address_id").c_str());
+		db_id_t parent_func_id=atoi(dbintr->getResultColumn("parent_function_id").c_str());
+		db_id_t orig_address_id=atoi(dbintr->getResultColumn("orig_address_id").c_str());
+		db_id_t fallthrough_address_id=atoi(dbintr->getResultColumn("fallthrough_address_id").c_str());
+		db_id_t targ_address_id=atoi(dbintr->getResultColumn("target_address_id").c_str());
+		db_id_t icfs_id=atoi(dbintr->getResultColumn("icfs_id").c_str());
+		db_id_t eh_pgm_id=atoi(dbintr->getResultColumn("ehpgm_id").c_str());
+		db_id_t eh_cs_id=atoi(dbintr->getResultColumn("ehcss_id").c_str());
+		std::string encoded_data=(dbintr->getResultColumn("data"));
+		std::string data=encoded_to_raw_string(encoded_data);
+		std::string callback=(dbintr->getResultColumn("callback"));
+		std::string comment=(dbintr->getResultColumn("comment"));
+		db_id_t indirect_branch_target_address_id = atoi(dbintr->getResultColumn("ind_target_address_id").c_str());
+		db_id_t doipid=atoi(dbintr->getResultColumn("doip_id").c_str());
+
+		std::string isIndStr=(dbintr->getResultColumn("ind_target_address_id"));
+
+                auto indTarg=(AddressID_t*)NULL;
+		if (indirect_branch_target_address_id != NOT_IN_DATABASE) 
+			indTarg = addrMap.at(indirect_branch_target_address_id);
+
+		auto parent_func=(Function_t*)NULL;
+		if(parent_func_id!= NOT_IN_DATABASE) parent_func=funcMap.at(parent_func_id);
+
+		Instruction_t *newinsn=new Instruction_t(instruction_id,
+			addrMap.at(aid),
+			parent_func,
+			orig_address_id,
+			data, callback, comment, indTarg, doipid);
+
+		if(eh_pgm_id != NOT_IN_DATABASE) newinsn->setEhProgram(ehpgmMap.at(eh_pgm_id));
+		if(eh_cs_id != NOT_IN_DATABASE) newinsn->setEhCallSite(ehcsMap.at(eh_cs_id));
+	
+		if(parent_func)
+		{
+			parent_func->GetInstructions().insert(newinsn);
+			newinsn->setFunction(funcMap.at(parent_func_id));
+		}
+
+//std::cout<<"Found address "<<aid<<"."<<std::endl;
+
+		idMap[instruction_id]=newinsn;
+		fallthroughs[instruction_id]=fallthrough_address_id;
+		targets[instruction_id]=targ_address_id;
+
+		addressToInstructionMap[aid] = newinsn;
+		insns.insert(newinsn);
+
+		if (icfs_id == NOT_IN_DATABASE)
+		{
+			newinsn->setIBTargets(NULL);
+		}
+		else
+		{
+			// keep track of instructions for which we have not yet
+			// resolved the ICFS
+			unresolvedICFS[newinsn] = icfs_id;
+		}
+
+		dbintr->moveToNextRow();
+	}
+
+	for(std::map<db_id_t,Instruction_t*>::const_iterator i=idMap.begin(); i!=idMap.end(); ++i)
+	{
+		Instruction_t *instr=(*i).second;
+		db_id_t fallthroughid=fallthroughs[instr->getBaseID()];
+		if(idMap[fallthroughid])	
+			instr->setFallthrough(idMap[fallthroughid]);
+		db_id_t targetid=targets[instr->getBaseID()];
+		if(idMap[targetid])	
+			instr->setTarget(idMap[targetid]);
+	}
+
+
+	return idMap;
+}
+
+void FileIR_t::ReadRelocsFromDB
+	(
+		std::map<db_id_t,BaseObj_t*> 	&objMap
+	)
+{
+	std::string q= "select * from " + fileptr->relocs_table_name + " ; ";
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+                db_id_t reloc_id=atoi(dbintr->getResultColumn("reloc_id").c_str());
+                int reloc_offset=atoi(dbintr->getResultColumn("reloc_offset").c_str());
+                std::string reloc_type=(dbintr->getResultColumn("reloc_type"));
+                db_id_t instruction_id=atoi(dbintr->getResultColumn("instruction_id").c_str());
+
+		// handle later?
+                //db_id_t doipid=atoi(dbintr->getResultColumn("doip_id").c_str());
+                db_id_t wrt_id=atoi(dbintr->getResultColumn("wrt_id").c_str());
+                uint32_t addend=atoi(dbintr->getResultColumn("addend").c_str());
+
+
+		BaseObj_t* wrt_obj=objMap[wrt_id];	 // might be null.
+		Relocation_t *reloc=new Relocation_t(reloc_id,reloc_offset,reloc_type,wrt_obj,addend);
+
+		assert(objMap[instruction_id]!=NULL);
+
+		objMap[instruction_id]->GetRelocations().insert(reloc);
+		relocs.insert(reloc);
+
+		dbintr->moveToNextRow();
+	}
+
+}
+
+
+void FileIR_t::writeToDB(ostream *verbose_logging)
+{
+//     	const auto WriteIRDB_start = clock();
+
+	const auto pqIntr=dynamic_cast<pqxxDB_t*>(dbintr);
+	assert(pqIntr);
+
+	//Resolve (assemble) any instructions in the registry.
+	assembleRegistry();
+
+	/* assign each item a unique ID */
+	setBaseIDS();
+
+	CleanupICFS(verbose_logging);
+
+	db_id_t j=-1;
+
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->instruction_table_name 	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->icfs_table_name 		+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->icfs_map_table_name 	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->function_table_name    	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->address_table_name     	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->relocs_table_name     	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->types_table_name     	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->scoop_table_name     	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->scoop_table_name+"_part2"+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->ehpgm_table_name     	+ string(" cascade;"));
+	dbintr->issueQuery(string("TRUNCATE TABLE ")+ fileptr->ehcss_table_name     	+ string(" cascade;"));
+
+	/* and now that everything has an ID, let's write to the DB */
+
+// write out the types
+	string q=string("");
+	for(auto t=types.begin(); t!=types.end(); ++t)
+	{
+		auto real_t=dynamic_cast<Type_t*>(*t);
+		assert(real_t);
+		q+=real_t->WriteToDB(fileptr,j); // @TODO: wtf is j?
+		if(q.size()>1024*1024)
+		{
+			dbintr->issueQuery(q);
+			q=string("");
+		}
+	}
+	dbintr->issueQuery(q);
+	
+
+// write out functions 
+	auto withHeader=true;
+	q=string("");
+	for(auto f=funcs.begin(); f!=funcs.end(); ++f)
+	{
+		auto real_f=dynamic_cast<Function_t*>(*f);
+		assert(real_f);
+		q+=real_f->WriteToDB(fileptr,j);
+		if(q.size()>1024*1024)
+		{
+			dbintr->issueQuery(q);
+			q=string("");
+		}
+	}
+	dbintr->issueQuery(q);
+
+
+// write out addresses
+	pqxx::tablewriter W_addrs(pqIntr->getTransaction(),fileptr->address_table_name);
+	for(const auto &a : addrs)
+	{
+		auto real_a=dynamic_cast<AddressID_t*>(a);
+		assert(real_a);
+		W_addrs << real_a->WriteToDB(fileptr,j,withHeader);
+	}
+	W_addrs.complete();
+
+// write out instructions
+
+	pqxx::tablewriter W(pqIntr->getTransaction(),fileptr->instruction_table_name);
+	for(auto i=insns.begin(); i!=insns.end(); ++i)
+	{	
+		auto insnp=dynamic_cast<Instruction_t*>(*i);
+		//DISASM disasm;
+		//Disassemble(insnp,disasm);
+		const auto p_disasm=DecodedInstruction_t::factory(insnp);
+		const auto& disasm=*p_disasm;
+
+		if(insnp->getOriginalAddressID() == NOT_IN_DATABASE)
+		{
+
+			// if(insnp->getFallthrough()==NULL && disasm.Instruction.BranchType!=RetType && disasm.Instruction.BranchType!=JmpType )
+			if(insnp->getFallthrough()==NULL && !disasm.isReturn() && !disasm.isUnconditionalBranch())
+			{
+				// instructions that fall through are required to either specify a fallthrough that's
+				// in the IRDB, or have an associated "old" instruction.  
+				// without these bits of information, the new instruction can't possibly execute correctly.
+				// and we won't have the information necessary to emit spri.
+
+				*verbose_logging << "NULL fallthrough: offending instruction:" << ((Instruction_t*)insnp)->getDisassembly() << " comment: " << ((Instruction_t*)insnp)->getComment() << endl;
+				assert(0);
+				abort();
+			}
+			//if(insnp->getTarget()==NULL && disasm.Instruction.BranchType!=0 && 
+			//	disasm.Instruction.BranchType!=RetType &&
+			//	// not an indirect branch
+			//	((disasm.Instruction.BranchType!=JmpType && disasm.Instruction.BranchType!=CallType) ||
+			//	 disasm.Argument1.ArgType&CONSTANT_TYPE))
+
+			if(insnp->getTarget()==NULL && disasm.isBranch() && !disasm.isReturn() &&
+				// not an indirect branch
+				( (!disasm.isUnconditionalBranch() && !disasm.isCall()) || disasm.getOperand(0)->isConstant())
+			  )
+			{
+				// direct branches are required to either specify a target that's
+				// in the IRDB, or have an associated "old" instruction.  
+				// without these bits of information, the new instruction can't possibly execute correctly.
+				// and we won't have the information necessary to emit spri.
+				*verbose_logging << "Call must have a target; offending instruction:" << ((Instruction_t*)insnp)->getDisassembly() << " comment: " << ((Instruction_t*)insnp)->getComment() << endl;
+				assert(0);
+				abort();
+			}
+		}
+
+		const auto &insn_values=insnp->WriteToDB(fileptr,j);
+		W << insn_values;
+
+	}
+	W.complete();
+
+
+// icfs 
+	for (auto it = GetAllICFS().begin(); it != GetAllICFS().end(); ++it)
+	{
+		ICFS_t* icfs = dynamic_cast<ICFS_t*>(*it);
+		assert(icfs);
+		string q = icfs->WriteToDB(fileptr);
+		dbintr->issueQuery(q);
+	}
+
+// scoops
+	for(auto it=scoops.begin(); it!=scoops.end(); ++it)
+	{
+		DataScoop_t* scoop = dynamic_cast<DataScoop_t*>(*it);
+		assert(scoop);
+		string q = scoop->WriteToDB(fileptr,j);
+		dbintr->issueQuery(q);
+	}
+
+// ehpgms 
+	pqxx::tablewriter W_eh(pqIntr->getTransaction(),fileptr->ehpgm_table_name);
+	for(const auto& i : eh_pgms)
+	{
+		W_eh << dynamic_cast<EhProgram_t*>(i)->WriteToDB(fileptr);
+	}
+	W_eh.complete();
+
+// eh css
+	for(const auto& i : eh_css)
+	{
+		string q = dynamic_cast<EhCallSite_t*>(i)->WriteToDB(fileptr);
+		dbintr->issueQuery(q);
+	}
+
+
+// all relocs
+	pqxx::tablewriter W_reloc(pqIntr->getTransaction(),fileptr->relocs_table_name);
+
+// eh css relocs
+	for(const auto& i : eh_css)
+	{
+		const auto &relocs=i->getRelocations();
+		for(auto& reloc : relocs)
+			W_reloc << dynamic_cast<Relocation_t*>(reloc)->WriteToDB(fileptr,dynamic_cast<BaseObj_t*>(i));
+	}
+
+// eh pgms relocs
+	for(const auto& i : eh_pgms)
+	{
+		const auto &relocs=i->getRelocations();
+		for(auto& reloc : relocs)
+			W_reloc << dynamic_cast<Relocation_t*>(reloc)->WriteToDB(fileptr,dynamic_cast<BaseObj_t*>(i));
+	}
+// scoops relocs
+	for(const auto& i : scoops)
+	{
+		const auto &relocs=i->getRelocations();
+		for(auto& reloc : relocs)
+			W_reloc << dynamic_cast<Relocation_t*>(reloc)->WriteToDB(fileptr,dynamic_cast<BaseObj_t*>(i));
+	}
+// write out instruction's relocs
+	for(const auto& i : insns)
+	{
+		const auto &relocs=i->getRelocations();
+		for(auto& reloc : relocs)
+			W_reloc << dynamic_cast<Relocation_t*>(reloc)->WriteToDB(fileptr,dynamic_cast<BaseObj_t*>(i));
+	}
+	W_reloc.complete();
+
+}
+
+
+db_id_t FileIR_t::getMaxBaseID() const
+{
+#define MAX(a,b) (((a)>(b)) ? (a) : (b))
+
+	/* find the highest database ID */
+	db_id_t j=0;
+	for(auto i=funcs.begin(); i!=funcs.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=addrs.begin(); i!=addrs.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=insns.begin(); i!=insns.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=relocs.begin(); i!=relocs.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=types.begin(); i!=types.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=scoops.begin(); i!=scoops.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=icfs_set.begin(); i!=icfs_set.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=eh_pgms.begin(); i!=eh_pgms.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+	for(auto i=eh_css.begin(); i!=eh_css.end(); ++i)
+		j=MAX(j,(*i)->getBaseID());
+
+	return j+1;	 // easy to off-by-one this so we do it for a user just in case.
+}
+
+void FileIR_t::setBaseIDS()
+{
+	auto j=getMaxBaseID();
+	/* increment past the max ID so we don't duplicate */
+	j++;
+	/* for anything that's not yet in the DB, assign an ID to it */
+	for(auto i=funcs.begin(); i!=funcs.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=addrs.begin(); i!=addrs.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=insns.begin(); i!=insns.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=relocs.begin(); i!=relocs.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=types.begin(); i!=types.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=scoops.begin(); i!=scoops.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=icfs_set.begin(); i!=icfs_set.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=eh_pgms.begin(); i!=eh_pgms.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+	for(auto i=eh_css.begin(); i!=eh_css.end(); ++i)
+		if((*i)->getBaseID()==NOT_IN_DATABASE)
+			(*i)->setBaseID(j++);
+}
+
+const  IRDB_SDK::ArchitectureDescription_t* IRDB_SDK::FileIR_t::getArchitecture() 
+{ 
+		return libIRDB::FileIR_t::archdesc; 
+}
+
+uint32_t IRDB_SDK::FileIR_t::getArchitectureBitWidth()
+{
+	return libIRDB::FileIR_t::archdesc->getBitWidth();
+}
+
+void FileIR_t::setArchitecture(const int width, const ADMachineType_t mt) 
+{
+	if(archdesc==NULL)
+		archdesc=new ArchitectureDescription_t;
+	archdesc->setBitWidth(width); 
+	archdesc->setMachineType(mt); 
+}	
+
+void FileIR_t::setArchitecture()
+{
+
+	/* the first 16 bytes of an ELF file define the magic number and ELF Class. */
+    	// unsigned char e_ident[16];
+	union 
+	{
+		Elf32_Ehdr ehdr32;
+		Elf64_Ehdr ehdr64;
+	} hdr_union;
+
+	auto myinter=BaseObj_t::GetInterface();
+	auto *mypqxxintr=dynamic_cast<pqxxDB_t*>(myinter);
+
+	const auto elfoid=getFile()->getELFOID();
+        pqxx::largeobjectaccess loa(mypqxxintr->getTransaction(), elfoid, PGSTD::ios::in);
+
+
+        loa.cread((char*)&hdr_union, sizeof(hdr_union));
+
+	const auto e_ident=hdr_union.ehdr32.e_ident;
+
+	libIRDB::FileIR_t::archdesc=new ArchitectureDescription_t;
+
+	auto is_elf=false;
+	auto is_pe=false;
+
+	if((e_ident[EI_MAG0]==ELFMAG0) && 
+	   (e_ident[EI_MAG1]==ELFMAG1) && 
+	   (e_ident[EI_MAG2]==ELFMAG2) && 
+	   (e_ident[EI_MAG3]==ELFMAG3))
+	{
+		is_elf=true;
+	}
+	else if((e_ident[EI_MAG0]=='M') &&
+	   (e_ident[EI_MAG1]=='Z'))
+	{
+		is_pe=true;
+	}
+	else
+	{
+		cerr << "File format magic number wrong:  is this an ELF, PE or CGC file? [" << e_ident[EI_MAG0] << " " << e_ident[EI_MAG1] << "]" << endl;
+		exit(-1);
+	}
+
+
+	if (is_pe) // libIRDB::FileIR_t::archdesc->getFileType() == IRDB_SDK::adftPE)
+	{
+		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);
+	}
+	else if(is_elf)
+	{
+		switch(e_ident[4])
+		{
+			case ELFCLASS32:
+			{
+
+				if(hdr_union.ehdr32.e_type == ET_DYN)
+					libIRDB::FileIR_t::archdesc->setFileType(IRDB_SDK::adftELFSO);
+				else
+					libIRDB::FileIR_t::archdesc->setFileType(IRDB_SDK::adftELFEXE);
+				libIRDB::FileIR_t::archdesc->setBitWidth(32);
+				if(hdr_union.ehdr32.e_machine!=EM_386)
+					throw std::invalid_argument("Arch not supported.  32-bit archs supported:  I386");
+				libIRDB::FileIR_t::archdesc->setMachineType(IRDB_SDK::admtI386);
+				break;
+			}
+			case ELFCLASS64:
+			{
+				if(hdr_union.ehdr64.e_type == ET_DYN)
+					libIRDB::FileIR_t::archdesc->setFileType(IRDB_SDK::adftELFSO);
+				else
+					libIRDB::FileIR_t::archdesc->setFileType(IRDB_SDK::adftELFEXE);
+				libIRDB::FileIR_t::archdesc->setBitWidth(64);
+				const auto mt= 
+					hdr_union.ehdr64.e_machine==EM_AARCH64 ? IRDB_SDK::admtAarch64 : 
+					hdr_union.ehdr64.e_machine==EM_X86_64  ? IRDB_SDK::admtX86_64 : 
+					throw std::invalid_argument("Arch not supported.  64-bit archs supported:  Aarch64, X86-64");
+				libIRDB::FileIR_t::archdesc->setMachineType(mt);
+				break;
+			}
+			default:
+				cerr << "Unknown ELF class " <<endl;
+				exit(-1);
+		}
+	}
+}
+
+ArchitectureDescription_t* FileIR_t::archdesc=NULL;
+
+std::map<db_id_t, Type_t*> FileIR_t::ReadTypesFromDB (TypeSet_t& types)
+{
+	std::map<db_id_t, Type_t*> tMap;
+
+	// 3 pass algorithm. Must be done in this exact order as:
+	//      aggregrate type depend on basic types
+	//      function type depends on both aggregate and basic types
+	//
+	// pass 1: retrieve all basic types
+	// pass 2: retrieve all aggregate types
+	// pass 3: retrieve all function types
+	//
+
+	// pass 1, get all the basic types first
+//	std::string q= "select * from " + fileptr->types_table_name + " WHERE ref_type_id = -1 AND ref_type_id2 = -1 AND pos = -1 order by type; ";
+
+	std::string q= "select * from " + fileptr->types_table_name + " WHERE ref_type_id = -1 order by type; ";
+
+//	cout << "pass1: query: " << q;
+
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+//  type_id            integer,     
+//  type               integer DEFAULT 0,    -- possible types (0: UNKNOWN)
+//  name               text DEFAULT '',      -- string representation of the type
+//  ref_type_id        integer DEFAULT -1,   -- for aggregate types and func
+//  pos                integer DEFAULT -1,   -- for aggregate types, position in aggregate
+//  ref_type_id2       integer DEFAULT -1,   -- for func types
+//  doip_id            integer DEFAULT -1    -- the DOIP
+
+		db_id_t tid=atoi(dbintr->getResultColumn("type_id").c_str());
+		IRDB_Type type=(IRDB_Type)atoi(dbintr->getResultColumn("type").c_str());
+		std::string name=dbintr->getResultColumn("name");
+		BasicType_t *t = NULL;	
+
+//		cout << "fileir::ReadFromDB(): pass1: " << name << endl;
+		switch(type) 
+		{
+			case IRDB_SDK::itUnknown:
+			case IRDB_SDK::itVoid:
+			case IRDB_SDK::itNumeric:
+			case IRDB_SDK::itVariadic:
+			case IRDB_SDK::itInt:
+			case IRDB_SDK::itChar:
+			case IRDB_SDK::itFloat:
+			case IRDB_SDK::itDouble:
+				t = new BasicType_t(tid, type, name);	
+				types.insert(t);
+				tMap[tid] = t;
+				break;
+
+			case IRDB_SDK::itPointer:
+				// do nothing for pointers
+				break;
+
+			default:
+				cerr << "ReadTypesFromDB(): ERROR: pass 1 should only see basic types or pointer"  << endl;
+				assert(0); 
+				break;						
+		}
+
+		dbintr->moveToNextRow();
+	} // end pass1
+
+	char query[2048];
+
+	// pass2 get pointers
+	sprintf(query,"select * from %s WHERE type = %d;", fileptr->types_table_name.c_str(), IRDB_SDK::itPointer);
+	dbintr->issueQuery(query);
+
+	while(!dbintr->isDone())
+	{
+		db_id_t tid=atoi(dbintr->getResultColumn("type_id").c_str());
+		IRDB_Type type=(IRDB_Type)atoi(dbintr->getResultColumn("type").c_str());
+		std::string name=dbintr->getResultColumn("name");
+		db_id_t ref1=atoi(dbintr->getResultColumn("ref_type_id").c_str());
+//		cout << "fileir::ReadFromDB(): pass2 (pointers): " << name << endl;
+		switch(type) 
+		{
+			case IRDB_SDK::itPointer:
+			{
+//						cout << "   pointer type: ref1: " << ref1 << endl;
+				Type_t *referentType = NULL;
+				if (ref1 >= 0) 
+				{
+					assert(tMap.count(ref1) > 0);
+					referentType = tMap[ref1];
+				}
+				PointerType_t *ptr = new PointerType_t(tid, referentType, name);	
+				types.insert(ptr);
+				tMap[tid] = ptr;
+			}
+			break;
+
+			default:
+				cerr << "ReadTypesFromDB(): ERROR: pass3: unhandled type id = "  << type << endl;
+				assert(0); // not yet handled
+				break;						
+
+		}
+
+		dbintr->moveToNextRow();
+	} // end pass3
+
+	// pass3 get all aggregates
+	sprintf(query,"select * from %s WHERE type = %d order by type_id, pos;", fileptr->types_table_name.c_str(), IRDB_SDK::itAggregate);
+	dbintr->issueQuery(query);
+
+	while(!dbintr->isDone())
+	{
+		db_id_t tid=atoi(dbintr->getResultColumn("type_id").c_str());
+		IRDB_Type type=(IRDB_Type)atoi(dbintr->getResultColumn("type").c_str());
+		std::string name=dbintr->getResultColumn("name");
+		db_id_t ref1=atoi(dbintr->getResultColumn("ref_type_id").c_str());
+		int pos=atoi(dbintr->getResultColumn("pos").c_str());
+		AggregateType_t *agg = NULL;	
+//		cout << "fileir::ReadFromDB(): pass3 (aggregates): " << name << endl;
+		switch(type) 
+		{
+			case IRDB_SDK::itAggregate:
+			{
+				if (tMap.count(tid) == 0)  // new aggregate
+				{	
+//		cout << "fileir::ReadFromDB(): pass3: new aggregate type: typeid: " << tid << " name: " << name << endl;
+					agg = new AggregateType_t(tid, name);	
+					types.insert(agg);
+					tMap[tid] = agg;
+				}
+				else
+					agg = dynamic_cast<AggregateType_t*>(tMap[tid]);
+
+				assert(agg);
+				// ref1 has the id of a basic type, look it up
+				Type_t *ref = tMap[ref1];
+				assert(ref);
+				agg->addAggregatedType(ref, pos);
+			}
+			break;
+
+			default:
+				cerr << "ReadTypesFromDB(): ERROR: pass2: unhandled type id = "  << type << endl;
+				assert(0); // not yet handled
+				break;						
+
+		}
+
+		dbintr->moveToNextRow();
+	} // end pass3
+
+	// pass4 get all functions
+	sprintf(query,"select * from %s WHERE type = %d;", fileptr->types_table_name.c_str(), IRDB_SDK::itFunc);
+	dbintr->issueQuery(query);
+
+	while(!dbintr->isDone())
+	{
+		db_id_t tid=atoi(dbintr->getResultColumn("type_id").c_str());
+		IRDB_Type type=(IRDB_Type)atoi(dbintr->getResultColumn("type").c_str());
+		std::string name=dbintr->getResultColumn("name");
+		db_id_t ref1=atoi(dbintr->getResultColumn("ref_type_id").c_str());
+		db_id_t ref2=atoi(dbintr->getResultColumn("ref_type_id2").c_str());
+		FuncType_t *fn = NULL;	
+
+		switch(type) 
+		{
+			case IRDB_SDK::itFunc:
+			{
+				assert(tMap.count(tid) == 0);
+
+				fn = new FuncType_t(tid, name);	
+				types.insert(fn);
+				tMap[tid] = fn;
+				assert(tMap[ref1]); // return type
+				assert(tMap[ref2]); // argument type (which is an aggregate)
+				fn->setReturnType(tMap[ref1]);
+				AggregateType_t *args = dynamic_cast<AggregateType_t*>(tMap[ref2]);
+				assert(args);
+				fn->setArgumentsType(args);
+				break;
+			}
+			default:
+				cerr << "ReadTypesFromDB(): ERROR: pass4: unhandled type id = "  << type << endl;
+				assert(0); // not yet handled
+				break;						
+
+		}
+
+		dbintr->moveToNextRow();
+	} // end pass4
+
+	return tMap;
+}
+
+void FileIR_t::ReadAllICFSFromDB(std::map<db_id_t,Instruction_t*> &addr2instMap,
+		std::map<Instruction_t*, db_id_t> &unresolvedICFS)
+{
+	std::map<db_id_t, ICFS_t*> icfsMap;
+
+	// retrieve all sets
+	std::string q= "select * from " + fileptr->icfs_table_name + " ; ";
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+		db_id_t icfs_id = atoi(dbintr->getResultColumn("icfs_id").c_str());
+		string statusString=dbintr->getResultColumn("icfs_status"); 
+
+		ICFS_t* icfs = new ICFS_t(icfs_id, statusString);		
+		GetAllICFS().insert(icfs);
+
+		icfsMap[icfs_id] = icfs;
+		dbintr->moveToNextRow();
+	}
+
+	ICFSSet_t all_icfs = GetAllICFS();
+
+	// for each set, populate its members
+	for (auto it = all_icfs.begin(); it != all_icfs.end(); ++it)
+	{
+		char query2[2048];
+		auto icfs = dynamic_cast<ICFS_t*>(*it);
+		assert(icfs);
+		int icfsid = icfs->getBaseID();
+		sprintf(query2,"select * from %s WHERE icfs_id = %d;", fileptr->icfs_map_table_name.c_str(), icfsid);
+		dbintr->issueQuery(query2);
+		while(!dbintr->isDone())
+		{
+			db_id_t address_id = atoi(dbintr->getResultColumn("address_id").c_str());
+			Instruction_t* instruction = addr2instMap[address_id];
+			if (instruction) 
+			{
+				icfs->insert(instruction);
+			}
+
+			// @todo: handle cross-file addresses
+			//        these are allowed by the DB schema but we don't yet handle them
+			// if we encounter an unresolved address, we should mark the ICFS
+			//      as unresolved
+
+			dbintr->moveToNextRow();
+		}					
+	}
+
+	// backpatch all unresolved instruction -> ICFS
+	std::map<Instruction_t*, db_id_t>::iterator uit;
+	for (auto uit = unresolvedICFS.begin(); uit != unresolvedICFS.end(); ++uit)
+	{
+		auto unresolved = dynamic_cast<Instruction_t*>(uit->first);
+		db_id_t icfs_id = uit->second;
+
+		assert(unresolved);
+
+		ICFS_t *icfs = icfsMap[icfs_id];
+		assert(icfs);
+
+		unresolved->setIBTargets(icfs);
+	}
+}
+
+void FileIR_t::GarbageCollectICFS(ostream* verbose_logging)
+{
+	auto used_icfs= ICFSSet_t();
+	// get the IBTarget of each instruction into used_icfs
+	transform(     ALLOF(insns), inserter(used_icfs, begin(used_icfs)), 
+	               [](const IRDB_SDK::Instruction_t* insn) -> IRDB_SDK::ICFS_t* { return insn->getIBTargets(); } 
+	         );
+	// we likely inserted null into the set, which we just will remove as a special ase.
+	used_icfs.erase(nullptr);
+
+	// update the list to include only the used ones.
+	icfs_set=used_icfs;
+}
+
+void FileIR_t::DedupICFS(ostream *verbose_logging)
+{
+	std::set<InstructionSet_t> unique_icfs;
+
+	auto& all_icfs=this->GetAllICFS();
+
+	// detect duplicate icfs
+	ICFSSet_t duplicates;
+	for(auto it=all_icfs.begin(); it!=all_icfs.end(); ++it)
+	{
+		auto p=dynamic_cast<ICFS_t*>(*it);
+		assert(p);
+		auto ret = unique_icfs.insert( *p );
+		if (!ret.second) {
+			duplicates.insert(p);
+		}
+	}
+
+	if (duplicates.size() > 0)
+	{
+		*verbose_logging << "FileIR_t::DedupICFS(): WARNING: " << dec << duplicates.size() << " duplicate ICFS out of " << all_icfs.size() << " total ICFS";
+		*verbose_logging << ". De-duplicating before committing to IRDB" << endl;
+	}
+
+	// remove duplicate icfs
+	for(auto it=duplicates.begin(); it!=duplicates.end(); ++it)
+	{
+		auto icfs=*it;
+		all_icfs.erase(icfs);
+	}
+
+	// build duplicate icfs map
+	std::map<IRDB_SDK::ICFS_t*, IRDB_SDK::ICFS_t*> duplicate_map;
+	for(auto it=duplicates.begin(); it!=duplicates.end(); ++it)
+	{
+		auto icfs = *it;
+		for(auto it=all_icfs.begin(); it!=all_icfs.end(); ++it)
+		{
+			auto t = *it;
+
+			assert(t);
+			if (*icfs == *t)
+			{
+				duplicate_map[icfs] = t;
+				*verbose_logging << "FileIR_t::DedupICFS(): remap: icfs id " << icfs->getBaseID() << " --> icsf id " << t->getBaseID() << endl;
+				break;
+			}
+		}
+	}
+
+	// reassign ibtargets 
+	for(auto it=this->GetInstructions().begin();
+		it!=this->GetInstructions().end();
+   		++it)
+	{
+		auto instr=*it;
+		if(instr->getIBTargets() && duplicate_map[instr->getIBTargets()])
+		{ 
+			instr->setIBTargets(duplicate_map[instr->getIBTargets()]);
+		}
+	}
+}
+
+void FileIR_t::CleanupICFS(ostream *verbose_logging)
+{
+	GarbageCollectICFS(verbose_logging);
+	DedupICFS(verbose_logging);
+}
+
+std::map<db_id_t,DataScoop_t*> FileIR_t::ReadScoopsFromDB
+        (
+                std::map<db_id_t,AddressID_t*> &addrMap,
+                std::map<db_id_t,Type_t*> &typeMap
+        )
+{
+/*
+  scoop_id           SERIAL PRIMARY KEY,        -- key
+  name               text DEFAULT '',           -- string representation of the type
+  type_id            integer,                   -- the type of the data, as an index into the table table.
+  start_address_id   integer,                   -- address id for start.
+  end_address_id     integer,                   -- address id for end
+  permissions        integer                    -- in umask format (bitmask for rwx)
+
+ */
+
+	std::map<db_id_t,DataScoop_t*> scoopMap;
+
+	//std::map<db_id_t,string> bonus_contents;
+	//
+	// read part 2 of the scoops.
+        //std::string q= "select * from " + fileptr->scoop_table_name + "_part2 ; ";
+        //dbintr->issueQuery(q);
+        //while(!dbintr->isDone())
+	//{
+        //        db_id_t sid=atoi(dbintr->getResultColumn("scoop_id").c_str());
+	//	bonus_contents[sid]=dbintr->getResultColumn("data");
+	//	dbintr->moveToNextRow();
+	//}
+
+
+
+	// read part 1 of the scoops, and merge in the part 2s
+	// scoop_id           SERIAL PRIMARY KEY,        -- key
+	// name               text DEFAULT '',           -- string representation of the type
+	// type_id            integer,                   -- the type of the data, as an index into the table table.
+	// start_address_id   integer,                   -- address id for start.
+	// end_address_id     integer,                   -- address id for end
+	// permissions        integer,                   -- in umask format (bitmask for rwx)
+	// relro              bit,                       -- is this scoop a relro scoop (i.e., is r/w until relocs are done).
+	// data               bytea                      -- the actual bytes of the scoop
+
+        string q= "select scoop_id,name,type_id,start_address_id,end_address_id,permissions,relro from " + fileptr->scoop_table_name + " ; ";
+        dbintr->issueQuery(q);
+        while(!dbintr->isDone())
+        {
+
+                db_id_t sid=atoi(dbintr->getResultColumn("scoop_id").c_str());
+                std::string name=dbintr->getResultColumn("name");
+                db_id_t type_id=atoi(dbintr->getResultColumn("type_id").c_str());
+		Type_t *type=typeMap[type_id];
+                db_id_t start_id=atoi(dbintr->getResultColumn("start_address_id").c_str());
+		AddressID_t* start_addr=addrMap[start_id];
+                db_id_t end_id=atoi(dbintr->getResultColumn("end_address_id").c_str());
+		AddressID_t* end_addr=addrMap[end_id];
+                int permissions=atoi(dbintr->getResultColumn("permissions").c_str());
+                bool is_relro=atoi(dbintr->getResultColumn("relro").c_str()) != 0 ;
+
+		DataScoop_t* newscoop=new DataScoop_t(sid,name,start_addr,end_addr,type,permissions,is_relro,"");
+		assert(newscoop);
+		GetDataScoops().insert(newscoop);
+		dbintr->moveToNextRow();
+
+		scoopMap[sid]=newscoop;
+	}
+
+	for(auto it=getDataScoops().begin(); it!=getDataScoops().end(); ++it)
+	{
+		DataScoop_t* scoop=dynamic_cast<DataScoop_t*>(*it);
+
+        	q= "select length(data) from " + fileptr->scoop_table_name + " where scoop_id='"+to_string(scoop->getBaseID())+"'; ";
+        	dbintr->issueQuery(q);
+		if(!dbintr->isDone())
+		{
+			int data_len=atoi(dbintr->getResultColumn("length").c_str());
+			for(int i=0;i<data_len;i+=SCOOP_CHUNK_SIZE)
+			{
+				string start_pos=to_string(i);
+				string len_to_get=to_string(SCOOP_CHUNK_SIZE);
+				string field="substr(data,"+start_pos+","+len_to_get+")";
+				q= "select "+field+" from " + fileptr->scoop_table_name + " where scoop_id='"+to_string(scoop->getBaseID())+"'; ";
+				dbintr->issueQuery(q);
+
+				scoop->getContents()+=dbintr->getResultColumn("substr");
+
+			}
+		}
+
+
+		// read part 2 from db
+        	q= "select length(data) from " + fileptr->scoop_table_name + "_part2 where scoop_id='"+to_string(scoop->getBaseID())+"'; ";
+        	dbintr->issueQuery(q);
+		if(!dbintr->isDone())
+		{
+			int part2_len=atoi(dbintr->getResultColumn("length").c_str());
+			for(int i=0;i<part2_len; i+=SCOOP_CHUNK_SIZE)
+			{
+				string start_pos=to_string(i);
+				string len_to_get=to_string(SCOOP_CHUNK_SIZE);
+				string field="substr(data,"+start_pos+","+len_to_get+")";
+				q= "select "+field+" from " + fileptr->scoop_table_name + "_part2 where scoop_id='"+to_string(scoop->getBaseID())+"'; ";
+				dbintr->issueQuery(q);
+
+				scoop->getContents()+=dbintr->getResultColumn("substr");
+
+			}
+		}
+	}
+	for(auto s : getDataScoops())
+	{
+		auto scoop=dynamic_cast<DataScoop_t*>(s);
+		assert(scoop->getContents().size() == scoop->getSize());
+	}
+
+
+	return scoopMap;
+}
+
+
+// Lookup a scoop by address
+IRDB_SDK::DataScoop_t* FileIR_t::findScoop(const IRDB_SDK::VirtualOffset_t &addr) const
+{
+	for(auto it=scoops.begin(); it!=scoops.end(); ++it)
+	{
+		auto s=dynamic_cast<DataScoop_t*>(*it);
+		// we're doing <= in both comparisons here intentionally.
+		// scoop addresses are the start/end address are inclusive
+		// so that start+size-1 == end.
+		if( s->getStart()->getVirtualOffset() <= addr && addr <= s->getEnd()->getVirtualOffset() )
+			return *it;
+	}
+	return NULL;
+}
+
+
+void FileIR_t::splitScoop(
+		IRDB_SDK::DataScoop_t *p_tosplit, 
+		const IRDB_SDK::VirtualOffset_t &addr, 
+		size_t size, 
+		IRDB_SDK::DataScoop_t* &p_before,
+		IRDB_SDK::DataScoop_t* &p_containing, 
+		IRDB_SDK::DataScoop_t* &p_after,
+		IRDB_SDK::DatabaseID_t *max_id_ptr	 /* in and out param */
+	)
+{
+	auto tosplit    = dynamic_cast<DataScoop_t*>(p_tosplit);
+	auto before     = dynamic_cast<DataScoop_t*>(p_before);
+	auto containing = dynamic_cast<DataScoop_t*>(p_containing);
+	auto after      = dynamic_cast<DataScoop_t*>(p_after);
+ 
+	// init output params.
+	before=containing=after=NULL;
+
+
+	if(tosplit->getStart()->getVirtualOffset() == addr &&
+		tosplit->getEnd()->getVirtualOffset() == addr+size-1)
+	{
+		// no split necessary
+		p_containing=tosplit;
+		return;
+	}
+
+	auto calcd_max_id=db_id_t(0);
+	if(max_id_ptr==NULL)
+		calcd_max_id = getMaxBaseID();
+
+	auto &max_id = max_id_ptr == NULL ? calcd_max_id : *max_id_ptr ;
+	
+	if(max_id==0)
+		max_id=calcd_max_id;
+
+	const auto multiple=(unsigned)1000;
+
+	// round to nearest multiple
+	const auto rounded_max = ((max_id + (multiple/2)) / multiple) * multiple;
+
+	max_id=rounded_max + multiple; // and skip forward so we're passed the highest.
+
+	const bool needs_before = addr!=tosplit->getStart()->getVirtualOffset();
+	const bool needs_after = addr+size-1 != tosplit->getEnd()->getVirtualOffset();
+
+
+	if(needs_before)
+	{
+		// setup before
+		// const AddressID_t* before_start=NULL;
+	
+		const auto before_start=new AddressID_t;
+		before_start->setBaseID(max_id++);
+		before_start->setFileID(tosplit->getStart()->getFileID());
+		before_start->setVirtualOffset(tosplit->getStart()->getVirtualOffset());
+
+		// const AddressID_t* before_end=new AddressID_t;
+		const auto before_end=new AddressID_t;
+		before_end->setBaseID(max_id++);
+		before_end->setFileID(tosplit->getStart()->getFileID());
+		before_end->setVirtualOffset(addr-1);
+
+		before=new DataScoop_t;
+		before->setBaseID(max_id++);
+		before->setName(tosplit->getName()+"3");
+		before->setStart(before_start);
+		before->setEnd(before_end);
+		before->setRawPerms(tosplit->getRawPerms());
+		before->getContents().resize(before_end->getVirtualOffset() - before_start->getVirtualOffset()+1);
+
+		// copy bytes
+		for(virtual_offset_t i=before_start->getVirtualOffset() ; i <= before_end->getVirtualOffset(); i++)
+			before->getContents()[i-before_start->getVirtualOffset()] = tosplit->getContents()[i-tosplit->getStart()->getVirtualOffset()];
+	
+
+		GetAddresses().insert(before_start);
+		GetAddresses().insert(before_end);
+		GetDataScoops().insert(before);
+	}
+
+	// setup containing
+	// AddressID_t* containing_start=new AddressID_t;
+	const auto containing_start=new AddressID_t;
+	containing_start->setBaseID(max_id++);
+	containing_start->setFileID(tosplit->getStart()->getFileID());
+	containing_start->setVirtualOffset(addr);
+
+	//AddressID_t* containing_end=new AddressID_t;
+	const auto containing_end=new AddressID_t;
+	containing_end->setBaseID(max_id++);
+	containing_end->setFileID(tosplit->getStart()->getFileID());
+	containing_end->setVirtualOffset(addr+size-1);
+
+	containing=new DataScoop_t;
+	containing->setBaseID(max_id++);
+	containing->setName(tosplit->getName()+"3");
+	containing->setStart(containing_start);
+	containing->setEnd(containing_end);
+	containing->setRawPerms(tosplit->getRawPerms());
+	containing->getContents().resize(containing_end->getVirtualOffset() - containing_start->getVirtualOffset()+1);
+	// copy bytes
+	for(virtual_offset_t i=containing_start->getVirtualOffset() ; i <= containing_end->getVirtualOffset(); i++)
+		containing->getContents()[i-containing_start->getVirtualOffset()] = tosplit->getContents()[i-tosplit->getStart()->getVirtualOffset()];
+
+	GetAddresses().insert(containing_start);
+	GetAddresses().insert(containing_end);
+	GetDataScoops().insert(containing);
+		
+
+	if(needs_after)
+	{
+		// setup after
+		// AddressID_t* after_start=new AddressID_t;
+		const auto after_start=new AddressID_t;
+		after_start->setBaseID(max_id++);
+		after_start->setFileID(tosplit->getStart()->getFileID());
+		after_start->setVirtualOffset(addr+size);
+
+		// AddressID_t* after_end=new AddressID_t;
+		const auto after_end=new AddressID_t;
+		after_end->setBaseID(max_id++);
+		after_end->setFileID(tosplit->getStart()->getFileID());
+		after_end->setVirtualOffset(tosplit->getEnd()->getVirtualOffset());
+
+		after=new DataScoop_t;
+		after->setBaseID(max_id++);
+		after->setName(tosplit->getName()+"3");
+		after->setStart(after_start);
+		after->setEnd(after_end);
+		after->setRawPerms(tosplit->getRawPerms());
+		after->getContents().resize(after_end->getVirtualOffset() - after_start->getVirtualOffset()+1);
+		// copy bytes
+		for(virtual_offset_t i=after_start->getVirtualOffset() ; i <= after_end->getVirtualOffset(); i++)
+			after->getContents()[i-after_start->getVirtualOffset()] = tosplit->getContents()[i-tosplit->getStart()->getVirtualOffset()];
+
+		GetAddresses().insert(after_start);
+		GetAddresses().insert(after_end);
+		GetDataScoops().insert(after);
+	}
+
+
+	// since tosplit is going away, we need to move every relocation from the 
+	// tosplit scoop into one of the others.  Iterate through each and 
+	// adjust the reloc's offset accordingly before inserting into the correct scoop's reloc set.
+	while(!tosplit->GetRelocations().empty())
+	{
+		auto reloc=dynamic_cast<Relocation_t*>(*(tosplit->getRelocations().begin()));
+		tosplit->GetRelocations().erase(tosplit->getRelocations().begin());
+
+		virtual_offset_t reloc_start=reloc->getOffset()+tosplit->getStart()->getVirtualOffset();
+
+		if(reloc_start < containing->getStart()->getVirtualOffset() )
+		{
+			before->GetRelocations().insert(reloc);
+		}
+		else if(reloc_start > containing->getEnd()->getVirtualOffset() )
+		{
+			reloc->setOffset(reloc_start-after->getStart()->getVirtualOffset());
+			after->GetRelocations().insert(reloc);
+		}
+		else
+		{
+			reloc->setOffset(reloc_start-containing->getStart()->getVirtualOffset());
+			containing->GetRelocations().insert(reloc);
+		}
+	
+	}
+
+	/* look at each relocation in the IR */
+	for(auto & r : GetRelocations())
+	{
+		if(r->getWRT()==tosplit)
+		{
+			const auto &addend=r->getAddend();
+			const auto containing_start_offset=(containing -> getStart()->getVirtualOffset() - 
+				tosplit->getStart()->getVirtualOffset());
+			const auto containing_end_offset=containing_start_offset+containing->getSize();
+			if(needs_before && addend<before->getSize())
+			{
+				r->setWRT(before);
+			}
+			else if( addend < containing_end_offset)
+			{
+				r->setWRT(containing);
+				r->setAddend(addend-containing_start_offset);
+			}
+			else 		
+			{
+				assert(needs_after);
+				const auto after_start_offset=(after -> getStart()->getVirtualOffset() - 
+					tosplit->getStart()->getVirtualOffset());
+				r->setWRT(after);
+				r->setAddend(addend-after_start_offset);
+			}
+		}
+	}
+	
+
+	GetAddresses().erase(tosplit->getStart());
+	GetAddresses().erase(tosplit->getEnd());
+	GetDataScoops().erase(tosplit);
+
+	delete tosplit->getStart();
+	delete tosplit->getEnd();
+	delete tosplit;
+
+	// set output parameters before returning.
+	p_before    = before;
+	p_containing= containing;
+	p_after     = after;
+
+	return;
+}
+
+
+IRDB_SDK::EhCallSite_t* FileIR_t::addEhCallSite_t(IRDB_SDK::Instruction_t* for_insn, const uint64_t enc, IRDB_SDK::Instruction_t* lp) 
+{
+	auto new_ehcs = new libIRDB::EhCallSite_t(BaseObj_t::NOT_IN_DATABASE, enc, lp);
+	GetAllEhCallSites().insert(new_ehcs);
+        for_insn->setEhCallSite(new_ehcs);
+	return new_ehcs;
+
+}
+
+IRDB_SDK::Relocation_t* FileIR_t::addNewRelocation(
+	IRDB_SDK::BaseObj_t* p_from_obj,
+	int32_t p_offset,
+	string p_type,
+	IRDB_SDK::BaseObj_t* p_wrt_obj,
+	int32_t p_addend)
+{
+	const auto from_obj=dynamic_cast<libIRDB::BaseObj_t*>(p_from_obj);
+	auto newreloc=new libIRDB::Relocation_t(BaseObj_t::NOT_IN_DATABASE, p_offset, p_type, p_wrt_obj, p_addend);
+	GetRelocations().insert(newreloc);
+	if(from_obj)
+		from_obj->GetRelocations().insert(newreloc);
+	
+	return newreloc;
+}
+
+EhProgram_t* FileIR_t::addEhProgram(
+	IRDB_SDK::Instruction_t* insn,
+	const uint64_t caf,
+	const int64_t daf,
+	const uint8_t rr,
+	const uint8_t p_ptrsize,
+	const EhProgramListing_t& p_cie_program,
+	const EhProgramListing_t& p_fde_program)
+{
+	auto newehpgm=new EhProgram_t(BaseObj_t::NOT_IN_DATABASE, caf,daf,rr,p_ptrsize, p_cie_program, p_fde_program);
+	assert(newehpgm);
+	GetAllEhPrograms().insert(newehpgm);
+	if(insn)
+		insn->setEhProgram(newehpgm);
+	return newehpgm;
+}
+
+
+
+void FileIR_t::removeScoop(IRDB_SDK::DataScoop_t* s)
+{
+	auto remove_reloc=[&](IRDB_SDK::Relocation_t* r) -> void
+        {
+                GetRelocations().erase(r);
+                delete r;
+        };
+
+        auto remove_address=[&](IRDB_SDK::AddressID_t* a) -> void
+        {
+                GetAddresses().erase(a);
+                for(auto &r : a->getRelocations()) remove_reloc(r);
+                for(auto &r : getRelocations()) assert(r->getWRT() != a);
+                delete a;
+        };
+
+        auto remove_scoop=[&] (IRDB_SDK::DataScoop_t* s) -> void
+        {
+                if(s==NULL)
+                        return;
+                GetDataScoops().erase(s);
+                remove_address(s->getStart());
+                remove_address(s->getEnd());
+                for(auto &r : s->getRelocations()) remove_reloc(r);
+                for(auto &r : GetRelocations()) assert(r->getWRT() != s);
+                delete s;
+        };
+
+	remove_scoop(s);
+}
+
+IRDB_SDK::AddressID_t* FileIR_t::addNewAddress(const IRDB_SDK::DatabaseID_t& myfileID, const IRDB_SDK::VirtualOffset_t& voff) 
+{
+	auto newaddr = new libIRDB::AddressID_t(BaseObj_t::NOT_IN_DATABASE, myfileID, voff);
+	GetAddresses().insert(newaddr);
+	return newaddr;
+}
+
+
+IRDB_SDK::ICFS_t* FileIR_t::addNewICFS(
+	IRDB_SDK::Instruction_t* insn,
+	const IRDB_SDK::InstructionSet_t& targets,
+	const IRDB_SDK::ICFSAnalysisStatus_t& status)
+{
+	auto newicfs=new libIRDB::ICFS_t(BaseObj_t::NOT_IN_DATABASE, status);
+	newicfs->setTargets(targets);
+	if(insn)
+		insn->setIBTargets(newicfs);
+	GetAllICFS().insert(newicfs);
+	return newicfs;
+}
+
+IRDB_SDK::Instruction_t* FileIR_t::addNewInstruction(
+	IRDB_SDK::AddressID_t* addr,
+	IRDB_SDK::Function_t* func,
+	const string& bits,
+	const string& comment,
+	IRDB_SDK::AddressID_t* indTarg)
+{
+	auto irdb_func    = dynamic_cast<libIRDB::Function_t* >(func);
+	auto irdb_addr    = dynamic_cast<libIRDB::AddressID_t*>(addr);
+	auto irdb_indTarg = dynamic_cast<libIRDB::AddressID_t*>(indTarg);
+
+	if(irdb_addr==nullptr)
+	{
+		irdb_addr=dynamic_cast<libIRDB::AddressID_t*>(addNewAddress(getFile()->getBaseID(), 0));
+	}
+
+	auto newinsn=new libIRDB::Instruction_t(BaseObj_t::NOT_IN_DATABASE, irdb_addr, irdb_func, BaseObj_t::NOT_IN_DATABASE, bits, "", comment, irdb_indTarg, BaseObj_t::NOT_IN_DATABASE);
+	
+	GetInstructions().insert(newinsn);
+
+	if(irdb_func)
+		irdb_func->GetInstructions().insert(newinsn);
+	return newinsn;
+}
+
+IRDB_SDK::DataScoop_t* FileIR_t::addNewDataScoop(
+	const string& p_name,
+	IRDB_SDK::AddressID_t* p_start,
+	IRDB_SDK::AddressID_t* p_end,
+	IRDB_SDK::Type_t* p_type,
+	uint8_t p_permissions,
+	bool p_is_relro,
+	const string& p_contents,
+	IRDB_SDK::DatabaseID_t id)
+{
+	auto irdb_start    = dynamic_cast<libIRDB::AddressID_t*>(p_start);
+	auto irdb_end      = dynamic_cast<libIRDB::AddressID_t*>(p_end);
+	auto irdb_type     = dynamic_cast<libIRDB::Type_t*>     (p_type);
+
+	auto newscoop=new libIRDB::DataScoop_t(id, p_name,irdb_start,irdb_end,irdb_type,p_permissions, p_is_relro, p_contents);
+	GetDataScoops().insert(newscoop);
+	return newscoop;
+}
+
+IRDB_SDK::EhProgram_t* FileIR_t::copyEhProgram(const IRDB_SDK::EhProgram_t& orig)
+{
+	const auto ehpgm=dynamic_cast<const libIRDB::EhProgram_t*>(&orig);
+	assert(ehpgm);
+	auto new_eh_pgm=new libIRDB::EhProgram_t(*ehpgm);
+        GetAllEhPrograms().insert(new_eh_pgm);
+	return new_eh_pgm;
+}
+
+
+
diff --git a/irdb-lib/libIRDB-core/src/function.cpp b/irdb-lib/libIRDB-core/src/function.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0be6aa95b661e68a9c3a8e004b0e7c287e79662a
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/function.cpp
@@ -0,0 +1,94 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <all.hpp>
+#include <irdb-util>
+#include <stdlib.h>
+
+using namespace libIRDB;
+using namespace std;
+
+Function_t::Function_t(db_id_t id, std::string myname, int size, int oa_size, bool useFP, bool isSafe, IRDB_SDK::FuncType_t *fn_type, IRDB_SDK::Instruction_t* entry)
+	: BaseObj_t(NULL), entry_point(dynamic_cast<Instruction_t*>(entry))
+{
+	setBaseID(id);
+	name=myname;
+	stack_frame_size=size;	
+	out_args_region_size=oa_size;
+	use_fp = useFP;
+	setSafe(isSafe);
+	function_type = dynamic_cast<FuncType_t*>(fn_type);
+	if(entry) assert(entry_point);
+	if(fn_type) assert(function_type);
+}
+
+string Function_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	assert(fid);
+
+	int entryid=NOT_IN_DATABASE;
+	if(entry_point)
+		entryid=entry_point->getBaseID();
+
+	if(getBaseID()==NOT_IN_DATABASE)
+		setBaseID(newid);
+
+    int function_type_id = NOT_IN_DATABASE;
+	if (getType())
+		function_type_id = getType()->getBaseID();	 
+
+	string q=string("insert into ")+fid->function_table_name + 
+		string(" (function_id, entry_point_id, name, stack_frame_size, out_args_region_size, use_frame_pointer, is_safe, type_id, doip_id) ")+
+		string(" VALUES (") + 
+		string("'") + to_string(getBaseID()) 		  + string("', ") + 
+		string("'") + to_string(entryid) 		  + string("', ") + 
+		string("'") + name 				  + string("', ") + 
+		string("'") + to_string(stack_frame_size) 	  + string("', ") + 
+	        string("'") + to_string(out_args_region_size) 	  + string("', ") + 
+	        string("'") + to_string(use_fp) 		  + string("', ") + 
+	        string("'") + to_string(is_safe) 		  + string("', ") + 
+	        string("'") + to_string(function_type_id) 	  + string("', ") + 
+		string("'") + to_string(getDoipID()) 		  + string("') ; ") ;
+
+	return q;
+}
+
+int Function_t::getNumArguments() const
+{
+	if (!function_type) return -1;
+	auto argtype = function_type->getArgumentsType();
+	if (argtype)
+		return argtype->getNumAggregatedTypes();
+	else
+		return -1;
+}
+
+void Function_t::setType(IRDB_SDK::FuncType_t *t)  
+{ 
+	function_type = dynamic_cast<FuncType_t*>(t); 
+	if(t) 
+		assert(function_type); 
+}
+
+IRDB_SDK::FuncType_t* Function_t::getType() const  
+{ 
+	return function_type; 
+}
+
diff --git a/irdb-lib/libIRDB-core/src/generate_spri.cpp b/irdb-lib/libIRDB-core/src/generate_spri.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d9754e9d27f9763aadefb38ec83e733db91b8ab6
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/generate_spri.cpp
@@ -0,0 +1,946 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <all.hpp>
+#include <irdb-util> // to_string function from libIRDB
+#include <iostream>
+#include <fstream>
+#include <stdlib.h>
+#include <map>
+#include <string.h>
+#include <assert.h>
+
+#undef EIP
+
+using namespace libIRDB;
+using namespace std;
+
+#if 0
+
+// forward decls for this file 
+static string qualified_addressify(FileIR_t* fileIRp, Instruction_t *insn);
+static string labelfy(IRDB_SDK::Instruction_t* insn);
+
+
+//
+// the set of insturctions that have control 
+// transfers to them (including fallthrough type control transfers) from instructions that do not need a spri rule.
+//
+static set<Instruction_t*> unmoved_insn_targets;
+	
+//
+// The set of all addresses that are ibts
+//
+static set <AddressID_t> ibts;
+
+//
+// map an instruction from the new variant back to the old variant;
+//
+static map<Instruction_t*,Instruction_t*> insnMap;
+
+//
+// does this instruction need a spri rule 
+//
+static bool needs_spri_rule(Instruction_t* newinsn,Instruction_t* oldinsn);
+
+
+//
+// return the address as a string for this instruction
+//
+static string addressify(Instruction_t* insn);
+
+
+//
+// determine if this branch has a short offset that can't be represented as a long branch
+//
+static bool needs_short_branch_rewrite(Instruction_t* newinsn, const DecodedInstruction_t &disasm)
+{
+	if   (	   (disasm.getMnemonic()== "jecxz" ) 
+		|| (disasm.getMnemonic()== "jrcxz" ) 
+		|| (disasm.getMnemonic()== "loop"  ) 
+		|| (disasm.getMnemonic()== "loopne") 
+		|| (disasm.getMnemonic()== "loope" ) )
+		return true;
+
+	/* 64-bit has more needs than this */
+	// if(disasm.Archi==32)
+	if(FileIR_t::getArchitectureBitWidth()==32)
+		return false;
+
+	// if(disasm.Instruction.BranchType==0)		/* non-branches, jumps, calls and returns don't need this rewrite */
+	if(!disasm.isBranch())
+		return false;
+	// if(disasm.Instruction.BranchType==JmpType)
+	if(disasm.isUnconditionalBranch())
+		return false;
+	// if(disasm.Instruction.BranchType==CallType)
+	if(disasm.isCall())
+		return false;
+	// if(disasm.Instruction.BranchType==RetType)
+	if(disasm.isReturn())
+		return false;
+
+	/* all other branches (on x86-64) need further checking */
+	if(!newinsn->getTarget())	/* no specified target, no need to modify it */
+		return false;
+	string new_target=labelfy(newinsn->getTarget());
+	if (new_target.c_str()[0]=='0')	/* if we're jumping back to the base instruction */
+		return true;
+	return false;
+}
+
+
+//
+// create a label for the given instruction
+//
+static string qualified_labelfy(FileIR_t* fileIRp, IRDB_SDK::Instruction_t* p_insn)
+{
+	auto insn=dynamic_cast<Instruction_t*>(p_insn);
+	if(!needs_spri_rule(insn, insnMap[insn]))
+		return qualified_addressify(fileIRp, insn);
+
+	return labelfy(insn);
+}
+
+static long long int label_offset=0;
+
+static void update_label_offset(FileIR_t *firp)
+{
+	int max=0;
+	for(auto insn : firp->GetInstructions())
+	{
+		if(insn->getBaseID()>max)
+			max=insn->getBaseID();
+	}
+	label_offset+=max+1;
+}
+
+static long long int IDToSPRIID(int id)
+{
+	return id+label_offset;
+}
+
+static string labelfy(IRDB_SDK::Instruction_t* p_insn)
+{
+	auto insn=dynamic_cast<Instruction_t*>(p_insn);
+
+	if(!needs_spri_rule(insn, insnMap[insn]))
+		return addressify(insn);
+
+	return string("LI_") + to_string(IDToSPRIID(insn->getBaseID()));
+}
+
+
+//
+// return the address for an instruction.  If the instruction has no absolute address, return the label for this instruction.
+//
+static string addressify(Instruction_t* insn)
+{
+	stringstream s;
+
+	Instruction_t* old_insn=insnMap[insn];
+	if(!old_insn)
+		return labelfy(insn);
+
+	s<<"0x"<<std::hex<<old_insn->getAddress()->getVirtualOffset();
+
+	return s.str();
+	
+
+}
+
+static string URLToFile(string url)
+{
+	auto loc=(size_t)0;
+
+	loc=url.find('/');
+	while(loc!=string::npos)
+	{
+		url=url.substr(loc+1,url.length()-loc-1);
+
+		loc=url.find('/');
+	}
+	// maybe need to check filename for odd characters 
+
+	return url;
+}
+
+static string qualify(FileIR_t* fileIRp)
+{
+	return URLToFile(fileIRp->getFile()->GetURL()) + "+" ;
+}
+
+
+static string qualify_address(FileIR_t* fileIRp, int addr)
+{
+	stringstream ss;
+	ss<< qualify(fileIRp) << "0x" << std::hex << (addr);
+	return ss.str();
+}
+
+static string better_qualify_address(FileIR_t* fileIRp, IRDB_SDK::AddressID_t* addr)
+{
+	db_id_t fileID=addr->getFileID();
+	virtual_offset_t off=addr->getVirtualOffset();
+
+	/* in theory, we could have an address from any file..
+	 * but this appears to be broken.  NOT_IN_DATABASE means we're in the spri address space,
+	 * so that's all i'm checking for for now.
+	 * do it the old way if it's in the DB, else the new way.
+	 */
+	if(fileID!=BaseObj_t::NOT_IN_DATABASE)
+		return qualify_address(fileIRp,off);
+
+	/* having a file not in the DB means we're int he spridd address space */
+	stringstream s;
+	s<<"spridd+0x"<<std::hex<<off;
+	return s.str();
+		
+}
+
+static string qualified_addressify(FileIR_t* fileIRp, Instruction_t *insn)
+{
+	string address=addressify(insn);
+	if(address.c_str()[0]=='0')
+		return qualify(fileIRp) + address;
+	return address;	
+	
+}
+
+static string get_short_branch_label(Instruction_t *newinsn)
+{
+	if (!newinsn)
+		return string("");
+	else
+		return "sj_" + labelfy(newinsn);
+}
+
+static string get_data_label(Instruction_t *newinsn)
+{
+	if (!newinsn)
+		return string("");
+	else
+		return "da_" + labelfy(newinsn);
+}
+
+static string getPostCallbackLabel(Instruction_t *newinsn)
+{
+	if (!newinsn)
+		return string("");
+	else
+		return "pcb_" + labelfy(newinsn);
+}
+
+
+static string get_relocation_string(FileIR_t* fileIRp, ostream& fout, int offset, string type, Instruction_t* insn) 
+{
+	stringstream ss;
+	ss<<labelfy(insn)<<" rl " << offset << " " << type <<  " " << URLToFile(fileIRp->getFile()->GetURL()) << endl;
+	return ss.str();
+}
+
+static void emit_relocation(FileIR_t* fileIRp, ostream& fout, int offset, string type, Instruction_t* insn) 
+{
+	fout<<"\t"<<get_relocation_string(fileIRp,fout,offset,type,insn);
+}
+
+
+/* return true if converted */
+bool convert_jump_for_64bit(Instruction_t* newinsn, string &final, string &emit_later, string new_target)
+{
+	/* skip for labeled addresses */
+	if (new_target.c_str()[0]!='0')
+		return false;
+
+	string datalabel=get_data_label(newinsn);
+
+	/* convert a "call <addr>" into "call qword [rel data_label] \n  data_label ** dq <addr>" */
+	int start=final.find(new_target,0);
+
+	string new_string=final.substr(0,start)+" qword [ rel " +datalabel + "]\n";
+	emit_later="\t"+ datalabel + " ** dq "+final.substr(start) + "\n";
+
+	final=new_string;
+
+	return true;
+}
+
+void emit_jump(FileIR_t* fileIRp, ostream& fout, const DecodedInstruction_t& disasm, Instruction_t* newinsn, Instruction_t *old_insn, string & original_target, string &emit_later)
+{
+
+	string label=labelfy(newinsn);
+	string complete_instr=disasm.getDisassembly();
+	string address_string=disasm.getOperand(0)->getString();
+
+
+	/* if we have a target instruction in the database */
+	if(newinsn->getTarget() || needs_short_branch_rewrite(newinsn,disasm))
+	{
+		/* change the target to be symbolic */
+
+		/* first get the new target */
+		string new_target;
+		if(newinsn->getTarget())
+			new_target=labelfy(newinsn->getTarget());
+		/* if this is a short branch, write this branch to jump to the next insn */
+		if(needs_short_branch_rewrite(newinsn,disasm))
+		{
+			new_target=get_short_branch_label(newinsn);
+
+			/* also get the real target if it's a short branch */
+			if(newinsn->getTarget())
+				original_target=labelfy(newinsn->getTarget());
+			else
+				original_target=address_string;
+		}
+
+		/* find the location in the disassembled string of the old target */
+		int start=complete_instr.find(address_string,0);
+
+		/* and build up a new string that has the label of the target instead of the address */
+		string final=complete_instr.substr(0,start) + new_target + complete_instr.substr(start+address_string.length());
+
+	
+		/* sanity, no segment registers for absolute mode */
+		//assert(disasm.Argument1.SegmentReg==0);
+
+		// if(disasm.Archi==64)
+		if(FileIR_t::getArchitectureBitWidth()==64)
+		{
+			auto converted=convert_jump_for_64bit(newinsn,final, emit_later,new_target);
+			(void)converted; // unused?
+		}
+
+		fout<<final<<endl;
+
+		if (new_target.c_str()[0]=='0')
+		{
+assert(0); 
+#if 0
+this will never work again?
+			// if we converted to an indirect jump, do a 64-bit reloc 
+			if(converted)
+			{
+				/* jumps have a 1-byte opcode */
+				string reloc=get_relocation_string(fileIRp, fout,0,"64-bit",newinsn);
+				emit_later=emit_later+"da_"+reloc;
+			}
+			// if we're jumping to an absolute address vrs a label, we will need a relocation for this jump instruction
+			else if(
+			   disasm.Instruction.Opcode==0xeb || 	 // jmp with 8-bit addr  -- should be recompiled to 32-bit
+			   disasm.Instruction.Opcode==0xe8 || 	 // jmp with 32-bit addr 
+			   disasm.Instruction.Opcode==0xe9 	 // call with 32-bit addr
+
+			)
+			{
+				/* jumps have a 1-byte opcode */
+				emit_relocation(fileIRp, fout,1,"32-bit",newinsn);
+			}
+			else
+			{
+				/* other jcc'often use a 2-byte opcode for far jmps (which is what spri will emit) */
+				emit_relocation(fileIRp, fout,2,"32-bit",newinsn);
+			}
+#endif
+		}
+	}
+	else 	/* this instruction has a target, but it's not in the DB */
+	{
+		/* so we'll just emit the instruction and let it go back to the application text. */	
+		fout<<complete_instr<<endl;
+// needs relocation info.
+#if 0
+// never to work again?
+		if(complete_instr.compare("call 0x00000000")==0 ||
+		   complete_instr.compare("jmp 0x00000000")==0
+		  )
+		{
+			// just ignore these bogus instructions.
+		}
+		else
+		{
+			if(
+			   disasm.Instruction.Opcode==0xeb || 	 // jmp with 8-bit addr 
+			   disasm.Instruction.Opcode==0xe8 || 	 // jmp with 32-bit addr 
+			   disasm.Instruction.Opcode==0xe9 	 // call with 32-bit addr
+			  )
+			{
+				emit_relocation(fileIRp, fout,1,"32-bit",newinsn);
+			}
+			else
+			{
+				// assert this is the "main" file and no relocation is necessary.
+				assert(strstr(fileIRp->getFile()->GetURL().c_str(),"a.ncexe")!=0);
+			}
+		}
+#endif
+	}
+}
+
+
+
+//
+// emit this instruction as spri code.
+//
+static string emit_spri_instruction(FileIR_t* fileIRp, Instruction_t *newinsn, ostream& fout, string &emit_later)
+{
+	string original_target;
+	Instruction_t* old_insn=insnMap[newinsn];
+
+	// disassemble using BeaEngine
+	// DISASM disasm;
+
+	/* Disassemble the instruction */
+	//int instr_len = Disassemble(newinsn,disasm);
+	const auto p_disasm=DecodedInstruction_t::factory(newinsn);
+	const auto &disasm=*p_disasm;
+
+	string label=labelfy(newinsn);
+	string complete_instr=disasm.getDisassembly(); 
+	string address_string=disasm.getOperand(0)->getString(); 
+
+	/* Emit any callback functions */
+	if (!newinsn->getCallback().empty())
+	{
+		fout << "\t"+label+"\t () " << newinsn->getCallback() << " # acts as a call <callback> insn" << endl;
+		fout << "\t"+ getPostCallbackLabel(newinsn)+" ** ";
+	}
+	else
+	{
+		fout << "\t"+label+"\t ** ";
+	}
+
+	/* emit the actual instruction from the database */
+	if( 
+	   strstr(disasm.getDisassembly().c_str(),"jmp far")!=0 || 
+	   strstr(disasm.getDisassembly().c_str(),"call far")!=0
+	  )
+	{
+		fout<<"\t hlt " << endl;
+	}
+
+	/* if it's a branch instruction, we have extra work to do */
+	else if(
+		//(disasm.Instruction.BranchType!=0) &&                  // it is a branch
+		//(disasm.Instruction.BranchType!=RetType) &&            // and not a return
+		//(disasm.Argument1.ArgType & CONSTANT_TYPE)!=0          // and has a constant argument type 1
+		disasm.isBranch()  &&
+		!disasm.isReturn() &&
+		disasm.getOperand(0)->isConstant() 
+	  )
+	{
+		emit_jump(fileIRp, fout, disasm,newinsn,old_insn, original_target, emit_later);
+	}
+	else
+	{
+		/* no target, just emit the instruction */
+
+		/* beaEngine kinda sucks and does some non-nasmness. */
+		
+		/* in this case, we look for an "lea <reg>, dword [ addr ]" and remove the "dword" part */
+		// if(strstr(disasm.CompleteInstr,"lea ") != NULL )
+
+// not needed after bea and/or libdecode fixes.
+#if 0
+		if(disasm.getMnemonic()=="lea")
+		{
+			char* a=strstr(disasm.CompleteInstr, "dword ");
+			if(a!=NULL)
+			{
+				a[0]=' ';	 // d
+				a[1]=' ';	 // w
+				a[2]=' ';	 // o
+				a[3]=' ';	 // r
+				a[4]=' ';	 // d
+			}
+		}
+
+
+		/* In this case, we look for "mov*x dstreg, srcreg" and convert srcreg to an appropriate size */
+		//if(	strstr(disasm.CompleteInstr, "movzx ") || 
+		//	strstr(disasm.CompleteInstr, "movsx ") )
+		if(	disasm.getMnemonic()== "movzx" || disasm.getMnemonic()== "movsx" )
+		{
+			if( disasm.Instruction.Opcode==0xfbe || disasm.Instruction.Opcode==0xfb6 ) 
+			{
+				char* comma=strstr(disasm.CompleteInstr, ",");
+				assert(comma);
+				if(comma[2]=='e' && comma[3]=='a' && comma[4]=='x') // eax -> al 
+					comma[2]=' ', comma[3],'a', comma[4]='l';
+				if(comma[2]=='e' && comma[3]=='b' && comma[4]=='x') // ebx -> bl 
+					comma[2]=' ', comma[3],'b', comma[4]='l';
+				if(comma[2]=='e' && comma[3]=='c' && comma[4]=='x') // ecx -> cl 
+					comma[2]=' ', comma[3],'c', comma[4]='l';
+				if(comma[2]=='e' && comma[3]=='d' && comma[4]=='x') // edx -> dl 
+					comma[2]=' ', comma[3],'d', comma[4]='l';
+				if(comma[2]=='e' && comma[3]=='s' && comma[4]=='p') // esp -> ah 
+					comma[2]=' ', comma[3],'a', comma[4]='h';
+				if(comma[2]=='e' && comma[3]=='b' && comma[4]=='p') // ebp -> bh 
+					comma[2]=' ', comma[3],'b', comma[4]='h';
+				if(comma[2]=='e' && comma[3]=='s' && comma[4]=='i') // esi -> ch 
+					comma[2]=' ', comma[3],'c', comma[4]='l';
+				if(comma[2]=='e' && comma[3]=='d' && comma[4]=='i') // edi -> dh 
+					comma[2]=' ', comma[3],'d', comma[4]='l';
+			}
+			else if( disasm.Instruction.Opcode==0xfbf || disasm.Instruction.Opcode==0xfb7 ) 
+			{
+#if 0
+/* this seems to be fixed in beaEngine -r175 */
+				char* comma=strstr(disasm.CompleteInstr, ",");
+				assert(comma);
+				if(strstr(&comma[2], "word [") == NULL)  // if it's not a memory operation 
+				{
+					assert(comma[2]=='e');
+					comma[2]=' ';
+				}
+#endif
+			}
+			else
+				assert(0); // wtf?
+		}
+		// look for an fld st0, st0, and convert it to fld st0 
+		else if(strcmp("fld st0 , st0", disasm.CompleteInstr)==0)
+		{
+			disasm.CompleteInstr[8]='\0';
+		}
+#endif
+			
+		fout<<disasm.getDisassembly();
+		fout<<endl;
+	}
+
+	//for(set<Relocation_t*>::iterator it=newinsn->GetRelocations().begin(); it!=newinsn->GetRelocations().end(); ++it)
+	for(auto this_reloc : newinsn->getRelocations())
+	{
+		//Relocation_t* this_reloc=*it;
+		emit_relocation(fileIRp, fout, this_reloc->getOffset(),this_reloc->getType(), newinsn);
+	}
+
+	auto IB_targets = newinsn->getIBTargets();
+	if (NULL != IB_targets) 
+	{
+		if (IB_targets->isComplete())
+		{
+			// Iterate through all IB targets and produce SPRI rules for IBTL (IB Target Limitation).
+			for (auto TargIter = IB_targets->begin(); TargIter != IB_targets->end(); ++TargIter)
+			{
+			    fout << "\t" << labelfy(newinsn) << " IL " << qualified_labelfy(fileIRp, *TargIter) << endl;
+			}
+		}
+	}
+
+	return original_target;
+
+}
+
+//
+// check to see if this instruction needs a spri rewrite rule.
+//
+static bool needs_spri_rule(Instruction_t* newinsn,Instruction_t* oldinsn)
+{
+	// check if this is an inserted instruction 
+	if(newinsn->getOriginalAddressID()==BaseObj_t::NOT_IN_DATABASE)
+		return true;
+
+	assert(oldinsn);
+	assert(newinsn->getOriginalAddressID()==oldinsn->getAddress()->getBaseID());
+
+
+	/* We moved the instruction  to a new address*/
+	if(newinsn->getAddress()->getVirtualOffset()!=oldinsn->getAddress()->getVirtualOffset())
+		return true;
+
+	/* We moved the instruction to a new file? */
+	if(newinsn->getAddress()->getFileID()!=oldinsn->getAddress()->getFileID())
+	{
+		//	
+		// coders:  verify this is OK before allowing an insn to change files. 
+		//
+		assert(0);
+		return true;
+	}
+
+
+	auto newFT=newinsn->getFallthrough();
+	auto newTG=newinsn->getTarget();
+	auto oldFT=oldinsn->getFallthrough();
+	auto oldTG=oldinsn->getTarget();
+
+	//
+	// check that both have a fallthrough or both don't have a fallthrough
+	//
+	if(!!newFT != !!oldFT)
+		return true;
+	//
+	// check that both have a target or both don't have a target
+	//
+	if(!!newTG != !!oldTG)
+		return true;
+
+	// if there's a fallthrough, but it is different, return true
+	if(newFT && newFT->getOriginalAddressID()!=oldFT->getAddress()->getBaseID())
+		return true;
+		
+	// if there's a target, but it is different, return true
+	if(newTG && newTG->getOriginalAddressID()!=oldTG->getAddress()->getBaseID())
+		return true;
+
+	// data bits themselves changed
+	if(newinsn->getDataBits() != oldinsn->getDataBits())
+		return true;
+
+	return false;
+}
+
+//
+// emit the spri rule to redirect this instruction.
+//
+static void emit_spri_rule(FileIR_t* fileIRp, Instruction_t* newinsn, ostream& fout, bool with_ilr)
+{
+	string emit_later;
+
+	Instruction_t* old_insn=insnMap[newinsn];
+
+	fout << endl << "# Orig addr: "<<addressify(newinsn)<<" insn_id: "<< std::dec 
+	     << newinsn->getBaseID()<<" with comment "<<newinsn->getComment()<<endl;
+	if (newinsn->getIndirectBranchTargetAddress())
+		fout << "# Orig addr: "<<addressify(newinsn)<<" indirect branch target: "
+		     <<newinsn->getIndirectBranchTargetAddress()->getVirtualOffset() << endl;
+
+	bool redirected_addr=false;
+	bool redirected_ibt=false;
+
+	// if it's the target of an unmodified instruction 
+	if( unmoved_insn_targets.find(newinsn) != unmoved_insn_targets.end() )
+	{
+		redirected_addr=true;
+		if(old_insn)
+		{
+			// then we will need a rule so that the unmodified instruction gets here correctly
+			fout << "# because its target of unmoved"<<endl;
+			fout << qualified_addressify(fileIRp, newinsn) <<" -> ."<<endl;
+		}
+	}
+
+	/* if this insn is an IB target, emit the redirect appropriately */
+	if (newinsn->getIndirectBranchTargetAddress()) 
+	{
+		redirected_ibt=true;
+		/* If the IBT address isn't this insns address, redirect appropriately.
+		 * If this insn isn't an unmoved insn target, always redirect appropriately.
+		 */
+		// if((old_insn && (*newinsn->getIndirectBranchTargetAddress()) != (*old_insn->getAddress()))
+		// 	||  !redirected_addr)
+		assert(0); // couldn't make this work
+		{
+			// use the better qualify address to check for file matches.
+			fout << "# because has indir "<<endl;
+			fout << better_qualify_address(fileIRp,newinsn->getIndirectBranchTargetAddress()) 
+			     <<" -> ."<<endl;
+		}
+
+		/* i don't understand this part.  hopefully this is right */
+		if(!newinsn->getCallback().empty())
+			fout << ". -> "<< getPostCallbackLabel(newinsn) <<endl;
+	}
+	// if there's a corresponding "old" instruction (i.e., in Variant 0, aka from the binary) 
+	if(old_insn)
+	{
+		/* the address of new insns with a corresponding old insn should start with 0x */
+		assert(addressify(newinsn).c_str()[0]=='0');
+
+		/* check to see if this address an IBT somewhere else */
+		/* and we havne't already redirected it */
+		if (ibts.find(*old_insn->getAddress()) == ibts.end() && !redirected_ibt && !redirected_addr)
+		{
+
+			// with ILR turned off, we don't try to redirect to 0
+			if(with_ilr)
+			{	
+				fout << "# eliding, no indirect targets"<<endl;
+				fout << qualified_addressify(fileIRp, newinsn) <<" -> 0x0 " <<endl; 
+			}
+			else
+			{
+				fout << "# skipping elide because ilr is off (in this module) and "
+					"no indirect targets, but emitting a rule anyhow"<<endl;
+				fout << qualified_addressify(fileIRp, newinsn) <<" ->  ."  << endl;
+			}
+			
+		}
+
+		// not yet handling callbacks on original instructions.
+		// this may be tricky because it seems we are overloading the indirect branch 
+		// target address to mean two things for instructions with callbacks.  Good luck if 
+		// you're reading this. 
+		assert(newinsn->getCallback().empty());
+		
+	}
+
+	string original_target=emit_spri_instruction(fileIRp, newinsn, fout, emit_later);
+
+
+	/* if there's a fallthrough instruction, jump to it. */
+	if(newinsn->getFallthrough())
+	{	
+		fout << ". -> " << qualified_labelfy(fileIRp,newinsn->getFallthrough())<<endl;
+	}
+	else
+	{
+		//DISASM disasm;
+		//disasm.Options = NasmSyntax + PrefixedNumeral + ShowSegmentRegs;
+		//disasm.Archi = fileIRp->getArchitectureBitWidth();
+		//disasm.EIP = (UIntPtr)newinsn->getDataBits().c_str();
+		//disasm.VirtualAddr = old_insn ? old_insn->getAddress()->getVirtualOffset() : 0;
+		const auto disasm=DecodedInstruction_t(newinsn);
+
+		/* Disassemble the instruction */
+		//int instr_len = Disasm(&disasm);
+		assert(disasm.valid());
+		int instr_len = disasm.length();
+		
+
+		//if( disasm.Instruction.BranchType!=RetType && disasm.Instruction.BranchType!=JmpType ) 
+		if( !disasm.isReturn() && !disasm.isUnconditionalBranch())
+		{
+			assert(old_insn);	/* it's an error to insert a new, non-unconditional branch instruction
+						 * and not specify it's fallthrough */
+			fout << ". -> " << qualify(fileIRp)<< "0x" << std::hex << old_insn->getAddress()->getVirtualOffset()+instr_len <<endl;
+		}
+	}
+
+	fout<<endl;
+
+	/* if the original target string is set, we need to emit 
+	 * a rule for this instruction so that short branches can always be resolved 
+	 */
+	if(!original_target.empty())
+	{
+		/* qualify this target if necessary */
+		if(original_target.c_str()[0]=='0')
+			original_target=qualify(fileIRp)+original_target;
+		fout << "\t" << get_short_branch_label(newinsn) << "\t -> \t " << original_target << endl;
+	}
+	fout<<emit_later<<endl;
+
+}
+
+
+
+//
+// generate a map from new instructions to old instructions
+//
+static void generate_insn_to_insn_maps(FileIR_t *fileIRp, FileIR_t *orig_fileIRp)
+{
+	static map<Instruction_t*,Instruction_t*> new_insnMap;
+	insnMap=new_insnMap; // re-init the global instruction map.
+
+	/* since a variant does not hold a pointer to the original code, we need to create that mapping 
+	 * we do it in two steps.  the first step is to make a map from ids in the original code 
+	 * to instructions in the original code 
+	 * the second step is to is to create the final mapping using the first map 
+	 */
+
+	map<db_id_t,Instruction_t*> idMap;
+
+	/* loop through each insn in the original program */
+	for(
+		auto it=orig_fileIRp->getInstructions().begin();
+		it!=orig_fileIRp->getInstructions().end();
+		++it
+	   )
+	{
+		/* get the insn */
+		Instruction_t *insn=*it;
+		assert(insn);
+
+		/* get it's ID */
+		db_id_t address_id=insn->getAddress()->getBaseID();
+		assert(address_id!=-1);
+
+		/* sanity check */
+		assert(insn->getAddress()->getFileID()!=-1);	
+		assert(insn->getAddress()->getVirtualOffset()!=0);	
+
+		/* insert into map */
+		idMap[address_id]=insn;
+	}
+
+	/* loop through the new variant and create the final mapping of new insn to old insn */
+	for(
+		std::set<Instruction_t*>::const_iterator it=fileIRp->GetInstructions().begin();
+		it!=fileIRp->GetInstructions().end();
+		++it
+	   )
+	{
+		/* get the insn */
+		Instruction_t *insn=*it;
+		assert(insn);
+
+		db_id_t orig_addr=insn->getOriginalAddressID();
+
+		/* no mapping if this is true */
+		if(orig_addr==-1)
+			continue;
+
+		assert(idMap[orig_addr]!=NULL);
+
+		insnMap[insn]=idMap[orig_addr];
+		
+	}
+}
+
+//
+// GenerateSPRI -  spri for the entire database
+//
+void FileIR_t::GenerateSPRI(ostream &fout, bool with_ilr)
+{
+	VariantID_t orig_varidp(progid.GetOriginalVariantID());
+	assert(orig_varidp.IsRegistered()==true);
+
+	for(
+		set<File_t*>::iterator it=orig_varidp.getFiles().begin();
+		it!=orig_varidp.getFiles().end();
+		++it
+	   )
+	{
+			File_t* the_file=*it;
+
+			if(the_file->getBaseID()==fileptr->orig_fid)
+			{
+				fout <<"# Generating spri for "<< the_file->GetURL()<<endl;
+
+				orig_variant_ir_p=new FileIR_t(orig_varidp,the_file);
+				this->GenerateSPRI(orig_variant_ir_p,fout,with_ilr);
+				delete orig_variant_ir_p;
+				orig_variant_ir_p=NULL;
+			}
+	
+	}
+
+
+
+}
+
+//
+// generate_IBT_set -- record all addresses in the program
+//
+static void generate_IBT_set(FileIR_t* fileIRp)
+{
+	ibts.clear();
+	for(
+		set<Instruction_t*>::const_iterator it=fileIRp->GetInstructions().begin();
+		it!=fileIRp->GetInstructions().end();
+		++it
+	   )
+	{
+		Instruction_t *insn=*it;
+		AddressID_t *ibt=insn->getIndirectBranchTargetAddress();
+
+		if(ibt)
+		{
+			ibts.insert(*ibt);
+		}
+
+	}
+
+}
+
+//
+// generate_unmoved_insn_targets_set --  create the set of insturctions that have control 
+// transfers to them (including fallthrough type control transfers) from instructions that do not need a spri rule.
+//
+static void generate_unmoved_insn_targets_set(FileIR_t* fileIRp)
+{
+	unmoved_insn_targets.clear();
+	for(
+		set<Instruction_t*>::const_iterator it=fileIRp->GetInstructions().begin();
+		it!=fileIRp->GetInstructions().end();
+		++it
+	   )
+	{
+		Instruction_t *insn=*it;
+
+		if(
+			// this instruction corresponds to an old instruction 
+			insnMap[insn] && 
+			// and we need a spri rule for it 
+			!needs_spri_rule(insn, insnMap[insn])
+		  )
+		{
+			unmoved_insn_targets.insert(insn->getTarget());
+			unmoved_insn_targets.insert(insn->getFallthrough());
+		}
+
+	}
+
+}
+#endif
+
+void FileIR_t::GenerateSPRI(FileIR_t *orig_fileIRp, ostream &fout, bool with_ilr)
+{
+	assert(0);
+	/*
+	//Resolve (assemble) any instructions in the registry.
+	AssembleRegistry();
+
+	// give 'this' a name
+	FileIR_t *fileIRp=this;
+
+	setBaseIDS(); // need unique ID to generate unique label name
+
+	// generate the map from new instruction to old instruction needed for this transform.
+	generate_insn_to_insn_maps(fileIRp, orig_fileIRp);
+
+	// generate the set of all indirect branch target addressses for this fileIR
+	generate_IBT_set(fileIRp);
+
+	// generate unmoved_insn_targets_set --  the set of instructions that have control 
+	// transfers to them (including fallthrough type control transfers) from instructions that do not need a spri rule.
+	generate_unmoved_insn_targets_set(fileIRp);
+
+	//
+	// for each instruction, compare the new instruction with the original instruction and see if 
+	// they are the same.  If so, do nothing, otherwise emit a rewrite rule for this instruction.
+	//
+	for(
+		std::set<Instruction_t*>::const_iterator it=fileIRp->GetInstructions().begin();
+		it!=fileIRp->GetInstructions().end();
+		++it
+	   )
+	{
+		Instruction_t* newinsn=*it;
+		Instruction_t* oldinsn=insnMap[newinsn];
+
+		assert(newinsn);
+
+		if(needs_spri_rule(newinsn,oldinsn))
+		{
+			emit_spri_rule(fileIRp,newinsn,fout,with_ilr);
+		}
+	}
+	update_label_offset(fileIRp);
+
+	fout<<"#DEBUG: maximum ID is "<<label_offset<<endl;
+	*/
+}
+
diff --git a/irdb-lib/libIRDB-core/src/icfs.cpp b/irdb-lib/libIRDB-core/src/icfs.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..f5e26b287aa6fa3a95f23e6264bda3c7702a0a1e
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/icfs.cpp
@@ -0,0 +1,98 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <all.hpp>
+#include <irdb-util>
+
+using namespace libIRDB;
+using namespace std;
+
+static string getICFSAnalysisStatus(const ICFS_Analysis_Status_t p_status) {
+	// strings must match DB definition
+	switch (p_status) {
+		case IRDB_SDK::iasAnalysisIncomplete:
+			return string("icfs_analysis_incomplete");
+			break;
+		case IRDB_SDK::iasAnalysisModuleComplete:
+			return string("icfs_analysis_module_complete");
+			break;
+		case IRDB_SDK::iasAnalysisComplete:
+			return string("icfs_analysis_complete");
+			break;
+		default:
+			return string("icfs_analysis_incomplete");
+			break;
+	}
+
+	std::cerr << "error: unknown ICFS analysis status: " << p_status << std::endl;
+	assert(0);
+}
+
+ICFS_t::ICFS_t(db_id_t p_set_id, const ICFS_Analysis_Status_t p_status) : BaseObj_t(NULL)
+{
+	setBaseID(p_set_id);
+	setAnalysisStatus(p_status);	
+}
+
+ICFS_t::ICFS_t(db_id_t p_set_id, const string p_statusString) : BaseObj_t(NULL)
+{
+	setBaseID(p_set_id);
+	if (p_statusString == "icfs_analysis_incomplete") {
+		setAnalysisStatus(IRDB_SDK::iasAnalysisIncomplete);	
+	} else if (p_statusString == "icfs_analysis_module_complete") {
+		setAnalysisStatus(IRDB_SDK::iasAnalysisModuleComplete);	
+	} else if (p_statusString == "icfs_analysis_complete") {
+		setAnalysisStatus(IRDB_SDK::iasAnalysisComplete);	
+	} else {
+		std::cerr << "error: unknown ICFS analysis status string: " << p_statusString << std::endl;
+		assert(0);
+	}
+}
+
+string ICFS_t::WriteToDB(File_t *fid)
+{
+	assert(fid);
+
+	db_id_t icfs_id = getBaseID();
+
+	string analysis_status = getICFSAnalysisStatus(getAnalysisStatus());
+
+	string q=string("insert into ") + fid->icfs_table_name + 
+		string(" (icfs_id, icfs_status) VALUES (") + 
+		string("'") + to_string(icfs_id) + string("', ") + 
+		string("'") + analysis_status + string("'); ") ;
+
+	for (InstructionSet_t::const_iterator it = this->begin(); 
+		it != this->end(); ++it)
+	{
+		auto insn = *it;		
+		assert(insn);
+
+		auto address_id = insn->getAddress()->getBaseID();
+
+		q += string("insert into ") + fid->icfs_map_table_name +
+			string(" (icfs_id, address_id) VALUES(") +
+			string("'") + to_string(icfs_id) + string("', ") +
+			string("'") + to_string(address_id) + string("'); ");
+	}
+
+	return q;
+}
+
diff --git a/irdb-lib/libIRDB-core/src/instruction.cpp b/irdb-lib/libIRDB-core/src/instruction.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..447f432de30535e300160d5231786c6e85ed0202
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/instruction.cpp
@@ -0,0 +1,264 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <all.hpp>
+#include <irdb-util>
+#include <stdlib.h> 
+#include <fstream>
+#include <sstream>
+#include <iomanip>
+#include <irdb-util>
+
+#undef EIP
+
+using namespace libIRDB;
+using namespace std;
+
+Instruction_t::Instruction_t() :
+	BaseObj_t(NULL), 
+	my_address(NULL),
+	my_function(NULL),
+	orig_address_id(NOT_IN_DATABASE),
+	fallthrough(NULL),
+	target(NULL),
+	data(""),
+	callback(""),
+	comment(""),
+	indTarg(NULL),
+	icfs(NULL),
+	eh_pgm(NULL),
+	eh_cs(NULL)
+{
+	setBaseID(NOT_IN_DATABASE);
+}
+
+Instruction_t::Instruction_t(db_id_t id, 
+		AddressID_t *addr, 
+		Function_t *func, 
+		db_id_t orig_id, 
+                std::string thedata, 
+		std::string my_callback, 
+		std::string my_comment, 
+		AddressID_t *my_indTarg, 
+		db_id_t doip_id) :
+
+	BaseObj_t(NULL), 
+	my_address(addr),
+	my_function(func),
+	orig_address_id(orig_id),
+	fallthrough(NULL),
+	target(NULL),
+	data(thedata),
+	callback(my_callback),
+	comment(my_comment),
+	indTarg(my_indTarg),
+	icfs(NULL),
+	eh_pgm(NULL),
+	eh_cs(NULL)
+{
+	setBaseID(id);
+}
+
+/*
+int Instruction_t::Disassemble(DISASM &disasm) const
+{
+ 
+  	memset(&disasm, 0, sizeof(DISASM));
+  
+  	disasm.Options = NasmSyntax + PrefixedNumeral;
+	disasm.Archi = FileIR_t::getArchitectureBitWidth();
+  	disasm.EIP = (UIntPtr) getDataBits().c_str();
+  	disasm.VirtualAddr = getAddress()->getVirtualOffset();
+  	int instr_len = Disasm(&disasm);
+ 	 
+  	return instr_len;  
+}
+*/
+
+std::string Instruction_t::getDisassembly() const
+{
+//  	DISASM disasm;
+//  	Disassemble(this,disasm);
+//  	return std::string(disasm.CompleteInstr);
+
+	const auto d=DecodedInstruction_t::factory(this);
+	return d->getDisassembly();
+}
+
+// 
+// Given an instruction in assembly, returns the raw bits in a string
+// On error, return the empty string
+//
+bool Instruction_t::assemble(string assembly)
+{
+   const string assemblyFile = "tmp.asm"; 
+   const string binaryOutputFile = "tmp.bin";
+
+   //remove any preexisting assembly or nasm generated files
+   string command = "rm -f " + assemblyFile;
+   command_to_stream(command,cout);
+   command = "rm -f "+assemblyFile+".bin";
+   command_to_stream(command,cout);
+
+   ofstream asmFile;
+   asmFile.open(assemblyFile.c_str());
+   if(!asmFile.is_open())
+   {
+     return false;
+   }
+
+   asmFile<<"BITS "<<std::dec<<FileIR_t::getArchitectureBitWidth()<<endl; 
+
+   asmFile<<assembly<<endl;
+   asmFile.close();
+
+   command = "nasm " + assemblyFile + " -o "+ binaryOutputFile;
+   command_to_stream(command,cout);
+
+    ifstream binreader;
+    unsigned int filesize;
+    binreader.open(binaryOutputFile.c_str(),ifstream::in|ifstream::binary);
+
+    if(!binreader.is_open())
+    {
+      return false;
+    }
+
+    binreader.seekg(0,ios::end);
+
+    filesize = binreader.tellg();
+
+    binreader.seekg(0,ios::beg);
+
+    if (filesize == 0) return false;
+
+    unsigned char *memblock = new unsigned char[filesize];
+
+    binreader.read((char*)memblock,filesize);
+    binreader.close();
+
+    string rawBits;
+    rawBits.resize(filesize);
+    for (auto i = 0U; i < filesize; ++i)
+      rawBits[i] = memblock[i];
+
+    // should erase those 2 files here
+
+    this->setDataBits(rawBits);
+    return true;
+}
+
+
+vector<string> Instruction_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	assert(fid);
+	assert(my_address);
+
+	if(getBaseID()==NOT_IN_DATABASE)
+		setBaseID(newid);
+
+	auto func_id=NOT_IN_DATABASE;
+	if(my_function) func_id=my_function->getBaseID();
+
+	auto ft_id=NOT_IN_DATABASE;
+	if(fallthrough) ft_id=fallthrough->getBaseID();
+
+	auto targ_id=NOT_IN_DATABASE;
+	if(target) targ_id=target->getBaseID();
+
+	auto icfs_id=NOT_IN_DATABASE;
+	if (icfs) icfs_id=icfs->getBaseID();
+
+	auto indirect_bt_id=NOT_IN_DATABASE;
+	if(indTarg) indirect_bt_id=indTarg->getBaseID();
+
+	auto eh_pgm_id=NOT_IN_DATABASE;
+	if(eh_pgm) eh_pgm_id=eh_pgm->getBaseID();
+
+	auto eh_css_id=NOT_IN_DATABASE;
+	if(eh_cs) eh_css_id=eh_cs->getBaseID();
+
+	ostringstream hex_data;
+	hex_data << setfill('0') << hex;;
+	for (size_t i = 0; i < data.length(); ++i)
+		hex_data << setw(2) << (int)(data[i]&0xff);
+
+
+	return {
+		to_string(getBaseID()),
+                to_string(my_address->getBaseID()),
+                to_string(func_id),
+                to_string(orig_address_id),
+                to_string(ft_id),
+                to_string(targ_id),
+                to_string(icfs_id),
+                to_string(eh_pgm_id),
+                to_string(eh_css_id),
+                hex_data.str(),
+                callback,
+                comment,
+                to_string(indirect_bt_id),
+                to_string(getDoipID()) };
+}
+
+
+/* return true if this instructino exits the function -- true if there's no function, because each instruction is it's own function? */
+bool Instruction_t::isFunctionExit() const 
+{ 
+	if(!my_function) 
+		return true;  
+
+	/* if there's a target that's outside this function */
+	auto target=getTarget();
+	if(target && target->getFunction()!=getFunction()) // !is_in_set(my_function->GetInstructions(),target))
+		return true;
+
+	/* if there's a fallthrough that's outside this function */
+	auto ft=getFallthrough();
+	if(fallthrough && ft->getFunction()!=getFunction()) // !is_in_set(my_function->GetInstructions(),ft))
+		return true;
+
+	/* some instructions have no next-isntructions defined in the db, and we call them function exits */
+	if(!target && !fallthrough)
+		return true;
+
+	return false;
+}
+
+IRDB_SDK::Function_t* Instruction_t::getFunction() const
+{
+	return my_function;
+}
+
+
+IRDB_SDK::EhProgram_t*  Instruction_t::getEhProgram()  const  { return eh_pgm; }
+IRDB_SDK::EhCallSite_t* Instruction_t::getEhCallSite() const  { return eh_cs; }
+IRDB_SDK::AddressID_t*  Instruction_t::getIndirectBranchTargetAddress() const { return indTarg; }
+
+void Instruction_t::setAddress     (IRDB_SDK::AddressID_t* newaddr)   { my_address=dynamic_cast<AddressID_t*>(newaddr); }
+void Instruction_t::setFunction    (IRDB_SDK::Function_t* func   )    { my_function=dynamic_cast<Function_t*>(func);}
+void Instruction_t::setFallthrough (IRDB_SDK::Instruction_t* i)       { fallthrough=dynamic_cast<Instruction_t*>(i); }
+void Instruction_t::setTarget      (IRDB_SDK::Instruction_t* i)       { target=dynamic_cast<Instruction_t*>(i); }
+void Instruction_t::setIBTargets   (IRDB_SDK::ICFS_t *p_icfs)         { icfs=dynamic_cast<ICFS_t*>(p_icfs); }
+void Instruction_t::setEhProgram(IRDB_SDK::EhProgram_t* orig)         { eh_pgm=dynamic_cast<EhProgram_t*>(orig); }
+void Instruction_t::setEhCallSite(IRDB_SDK::EhCallSite_t* orig)       { eh_cs=dynamic_cast<EhCallSite_t*>(orig); }
+void Instruction_t::setIndirectBranchTargetAddress(IRDB_SDK::AddressID_t* myIndTarg)  { indTarg=dynamic_cast<AddressID_t*>(myIndTarg); }
+
+
diff --git a/irdb-lib/libIRDB-core/src/operand_csarm.cpp b/irdb-lib/libIRDB-core/src/operand_csarm.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..01a20a17d5061ca3ed15f602c074ed6b06caeea2
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/operand_csarm.cpp
@@ -0,0 +1,310 @@
+
+#include <libIRDB-core.hpp>
+#include <memory>
+#include <decode_base.hpp>
+#include <decode_csarm.hpp>
+#include <operand_base.hpp>
+#include <operand_csarm.hpp>
+
+
+using namespace std;
+using namespace libIRDB;
+
+#include <capstone.h>
+static const auto ARM64_REG_PC=(arm64_reg)(ARM64_REG_ENDING+1);
+
+
+DecodedOperandCapstoneARM64_t::DecodedOperandCapstoneARM64_t( const shared_ptr<void> & p_my_insn, uint8_t p_op_num)
+	:
+	my_insn(p_my_insn),
+	op_num(p_op_num)
+{
+	
+}
+
+DecodedOperandCapstoneARM64_t::~DecodedOperandCapstoneARM64_t()
+{
+}
+
+
+bool DecodedOperandCapstoneARM64_t::isConstant() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+	return op.type==ARM64_OP_IMM;
+}
+
+uint64_t DecodedOperandCapstoneARM64_t::getConstant() const
+{
+	if(!isConstant()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-constant operand");
+	
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+	return op.imm;
+}
+
+string DecodedOperandCapstoneARM64_t::getString() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        const auto handle=DecodedInstructionCapstoneARM64_t::cs_handle->getHandle();
+
+        switch(op.type)
+        {
+                case ARM64_OP_REG:
+                        return string(cs_reg_name(handle, op.reg));
+                case ARM64_OP_REG_MRS:
+                case ARM64_OP_REG_MSR:
+                case ARM64_OP_FP:
+			return string("fpcr");
+                case ARM64_OP_IMM:
+                        return to_string(op.imm);
+                case ARM64_OP_MEM:
+                {
+			string ret_val;
+			if (op.mem.base != ARM64_REG_INVALID)
+				ret_val+=cs_reg_name(handle, op.mem.base);
+
+			if (op.mem.index != ARM64_REG_INVALID)
+				ret_val+=string(" + ") +cs_reg_name(handle, op.mem.index);
+
+			if (op.mem.disp != 0)
+				ret_val+=" + "+ to_string(op.mem.disp);
+
+			if(ret_val=="")
+				return "0";
+
+			return ret_val;
+		}
+                default:
+                        assert(0);
+        }
+}
+
+bool DecodedOperandCapstoneARM64_t::isRegister() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+	return op.type==ARM64_OP_REG;
+}
+
+bool DecodedOperandCapstoneARM64_t::isGeneralPurposeRegister() const
+{
+	const auto gp_regs=set<arm64_reg>({
+		ARM64_REG_X29, ARM64_REG_X30, ARM64_REG_SP, ARM64_REG_WSP, ARM64_REG_WZR, ARM64_REG_XZR,
+		ARM64_REG_W0, ARM64_REG_W1, ARM64_REG_W2, ARM64_REG_W3, ARM64_REG_W4, ARM64_REG_W5, ARM64_REG_W6, ARM64_REG_W7,
+        	ARM64_REG_W8, ARM64_REG_W9, ARM64_REG_W10, ARM64_REG_W11, ARM64_REG_W12, ARM64_REG_W13, ARM64_REG_W14, ARM64_REG_W15,
+        	ARM64_REG_W16, ARM64_REG_W17, ARM64_REG_W18, ARM64_REG_W19, ARM64_REG_W20, ARM64_REG_W21, ARM64_REG_W22, ARM64_REG_W23, 
+		ARM64_REG_W24, ARM64_REG_W25, ARM64_REG_W26, ARM64_REG_W27, ARM64_REG_W28, ARM64_REG_W29, ARM64_REG_W30, 
+		ARM64_REG_X0, ARM64_REG_X1, ARM64_REG_X2, ARM64_REG_X3, ARM64_REG_X4, ARM64_REG_X5, ARM64_REG_X6, ARM64_REG_X7,
+		ARM64_REG_X8, ARM64_REG_X9, ARM64_REG_X10, ARM64_REG_X11, ARM64_REG_X12, ARM64_REG_X13, ARM64_REG_X14, ARM64_REG_X15,
+		ARM64_REG_X16, ARM64_REG_X17, ARM64_REG_X18, ARM64_REG_X19, ARM64_REG_X20, ARM64_REG_X21, ARM64_REG_X22, ARM64_REG_X23,
+		ARM64_REG_X24, ARM64_REG_X25, ARM64_REG_X26, ARM64_REG_X27, ARM64_REG_X28,
+	});
+
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return isRegister() &&  gp_regs.find(op.reg)!=end(gp_regs);
+
+}
+
+bool DecodedOperandCapstoneARM64_t::isMmxRegister() const
+{
+	return false;
+}
+
+bool DecodedOperandCapstoneARM64_t::isFpuRegister() const
+{
+	const auto fpu_regs=set<arm64_reg>({
+		ARM64_REG_B0, ARM64_REG_B1, ARM64_REG_B2, ARM64_REG_B3, ARM64_REG_B4, ARM64_REG_B5, ARM64_REG_B6, ARM64_REG_B7,
+        	ARM64_REG_B8, ARM64_REG_B9, ARM64_REG_B10, ARM64_REG_B11, ARM64_REG_B12, ARM64_REG_B13, ARM64_REG_B14, ARM64_REG_B15,
+        	ARM64_REG_B16, ARM64_REG_B17, ARM64_REG_B18, ARM64_REG_B19, ARM64_REG_B20, ARM64_REG_B21, ARM64_REG_B22, ARM64_REG_B23,
+        	ARM64_REG_B24, ARM64_REG_B25, ARM64_REG_B26, ARM64_REG_B27, ARM64_REG_B28, ARM64_REG_B29, ARM64_REG_B30, ARM64_REG_B31,
+		ARM64_REG_H0, ARM64_REG_H1, ARM64_REG_H2, ARM64_REG_H3, ARM64_REG_H4, ARM64_REG_H5, ARM64_REG_H6, ARM64_REG_H7, 
+		ARM64_REG_H8, ARM64_REG_H9, ARM64_REG_H10, ARM64_REG_H11, ARM64_REG_H12, ARM64_REG_H13, ARM64_REG_H14, ARM64_REG_H15, 
+		ARM64_REG_H16, ARM64_REG_H17, ARM64_REG_H18, ARM64_REG_H19, ARM64_REG_H20, ARM64_REG_H21, ARM64_REG_H22, ARM64_REG_H23, 
+		ARM64_REG_H24, ARM64_REG_H25, ARM64_REG_H26, ARM64_REG_H27, ARM64_REG_H28, ARM64_REG_H29, ARM64_REG_H30, ARM64_REG_H31, 
+	        ARM64_REG_D0, ARM64_REG_D1, ARM64_REG_D2, ARM64_REG_D3, ARM64_REG_D4, ARM64_REG_D5, ARM64_REG_D6, ARM64_REG_D7,
+        	ARM64_REG_D8, ARM64_REG_D9, ARM64_REG_D10, ARM64_REG_D11, ARM64_REG_D12, ARM64_REG_D13, ARM64_REG_D14, ARM64_REG_D15,
+		ARM64_REG_D16, ARM64_REG_D17, ARM64_REG_D18, ARM64_REG_D19, ARM64_REG_D20, ARM64_REG_D21, ARM64_REG_D22, ARM64_REG_D23,
+		ARM64_REG_D24, ARM64_REG_D25, ARM64_REG_D26, ARM64_REG_D27, ARM64_REG_D28, ARM64_REG_D29, ARM64_REG_D30, ARM64_REG_D31,
+	        ARM64_REG_H0, ARM64_REG_H1, ARM64_REG_H2, ARM64_REG_H3, ARM64_REG_H4, ARM64_REG_H5, ARM64_REG_H6, ARM64_REG_H7,
+		ARM64_REG_H8, ARM64_REG_H9, ARM64_REG_H10, ARM64_REG_H11, ARM64_REG_H12, ARM64_REG_H13, ARM64_REG_H14, ARM64_REG_H15,
+		ARM64_REG_H16, ARM64_REG_H17, ARM64_REG_H18, ARM64_REG_H19, ARM64_REG_H20, ARM64_REG_H21, ARM64_REG_H22, ARM64_REG_H23,
+		ARM64_REG_H24, ARM64_REG_H25, ARM64_REG_H26, ARM64_REG_H27, ARM64_REG_H28, ARM64_REG_H29, ARM64_REG_H30, ARM64_REG_H31,
+	        ARM64_REG_Q0, ARM64_REG_Q1, ARM64_REG_Q2, ARM64_REG_Q3, ARM64_REG_Q4, ARM64_REG_Q5, ARM64_REG_Q6, ARM64_REG_Q7,
+		ARM64_REG_Q8, ARM64_REG_Q9, ARM64_REG_Q10, ARM64_REG_Q11, ARM64_REG_Q12, ARM64_REG_Q13, ARM64_REG_Q14, ARM64_REG_Q15,
+		ARM64_REG_Q16, ARM64_REG_Q17, ARM64_REG_Q18, ARM64_REG_Q19, ARM64_REG_Q20, ARM64_REG_Q21, ARM64_REG_Q22, ARM64_REG_Q23,
+		ARM64_REG_Q24, ARM64_REG_Q25, ARM64_REG_Q26, ARM64_REG_Q27, ARM64_REG_Q28, ARM64_REG_Q29, ARM64_REG_Q30, ARM64_REG_Q31,
+		ARM64_REG_S0, ARM64_REG_S1, ARM64_REG_S2, ARM64_REG_S3, ARM64_REG_S4, ARM64_REG_S5, ARM64_REG_S6, ARM64_REG_S7,
+		ARM64_REG_S8, ARM64_REG_S9, ARM64_REG_S10, ARM64_REG_S11, ARM64_REG_S12, ARM64_REG_S13, ARM64_REG_S14, ARM64_REG_S15,
+		ARM64_REG_S16, ARM64_REG_S17, ARM64_REG_S18, ARM64_REG_S19, ARM64_REG_S20, ARM64_REG_S21, ARM64_REG_S22, ARM64_REG_S23,
+		ARM64_REG_S24, ARM64_REG_S25, ARM64_REG_S26, ARM64_REG_S27, ARM64_REG_S28, ARM64_REG_S29, ARM64_REG_S30, ARM64_REG_S31,
+	});
+
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return isRegister() &&  fpu_regs.find(op.reg)!=end(fpu_regs);
+}
+
+bool DecodedOperandCapstoneARM64_t::isSseRegister() const
+{
+	return false;
+}
+
+bool DecodedOperandCapstoneARM64_t::isAvxRegister() const
+{
+	return false;
+}
+
+bool DecodedOperandCapstoneARM64_t::isZmmRegister() const
+{
+	return false;
+}
+
+bool DecodedOperandCapstoneARM64_t::isSpecialRegister() const
+{
+	const auto special_regs=set<arm64_reg>({
+		ARM64_REG_NZCV,
+	});
+
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return isRegister() &&  special_regs.find(op.reg)!=end(special_regs);
+	return false;
+}
+
+bool DecodedOperandCapstoneARM64_t::isSegmentRegister() const
+{
+	return false;
+}
+
+
+
+uint32_t DecodedOperandCapstoneARM64_t::getRegNumber() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+	return op.reg;
+}
+
+bool DecodedOperandCapstoneARM64_t::isMemory() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return op.type==ARM64_OP_MEM;
+
+}
+
+bool DecodedOperandCapstoneARM64_t::hasBaseRegister() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return isMemory() && op.mem.base!=ARM64_REG_INVALID;
+
+}
+
+bool DecodedOperandCapstoneARM64_t::hasIndexRegister() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return isMemory() && op.mem.index!=ARM64_REG_INVALID;
+}
+
+uint32_t DecodedOperandCapstoneARM64_t::getBaseRegister() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return op.mem.base;
+}
+
+uint32_t DecodedOperandCapstoneARM64_t::getIndexRegister() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return op.mem.index;
+}
+
+uint32_t DecodedOperandCapstoneARM64_t::getScaleValue() const
+{
+	assert(0);
+}
+
+bool DecodedOperandCapstoneARM64_t::hasMemoryDisplacement() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return op.mem.disp!=0;
+
+} // end of DecodedOperandCapstoneARM64_t::hasMemoryDisplacement()
+
+virtual_offset_t DecodedOperandCapstoneARM64_t::getMemoryDisplacement() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+        return op.mem.disp;
+}
+
+bool DecodedOperandCapstoneARM64_t::isPcrel() const
+{
+	const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+
+	// covers ldr, ldrsw, prfm
+	// note: capstone's reports ldr, ldrsw, and prfm as using an imm, when they actually access memory.
+	// jdh fixed this in the IRDB's Disassemble routine
+	if(isMemory() && op.mem.base==ARM64_REG_PC)
+		return true;
+
+	const auto mnemonic=string(the_insn->mnemonic);
+	const auto is_adr_type= mnemonic=="adr"  || mnemonic=="adrp";
+	if(is_adr_type && op.type==ARM64_OP_IMM)
+		return true;
+
+	return false;	 // no PC as general purpose reg.
+}
+
+/* in bytes */
+uint32_t DecodedOperandCapstoneARM64_t::getMemoryDisplacementEncodingSize() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+	assert(0);
+}
+
+uint32_t DecodedOperandCapstoneARM64_t::getArgumentSizeInBytes() const
+{
+	return false;
+}
+
+uint32_t DecodedOperandCapstoneARM64_t::getArgumentSizeInBits() const
+{
+        return getArgumentSizeInBytes()*8;
+}
+
+bool DecodedOperandCapstoneARM64_t::hasSegmentRegister() const
+{
+	return false;
+}
+
+uint32_t DecodedOperandCapstoneARM64_t::getSegmentRegister() const
+{
+	throw std::logic_error(string("Cannot ")+__FUNCTION__+"  on ARM architecture");
+}
+
+bool DecodedOperandCapstoneARM64_t::isRead() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+	return (op.access & CS_AC_READ)!=0;
+}
+
+bool DecodedOperandCapstoneARM64_t::isWritten() const
+{	
+	// default: use capstone's advice.
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->arm64.operands[op_num]);
+	return (op.access & CS_AC_WRITE)!=0;
+}
diff --git a/irdb-lib/libIRDB-core/src/operand_csx86.cpp b/irdb-lib/libIRDB-core/src/operand_csx86.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ce863a9ef45d60a35f2354a6fc2a5f81e0b65e91
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/operand_csx86.cpp
@@ -0,0 +1,820 @@
+
+#include <libIRDB-core.hpp>
+#include <memory>
+#include <decode_base.hpp>
+#include <decode_csx86.hpp>
+#include <operand_base.hpp>
+#include <operand_csx86.hpp>
+
+
+
+using namespace std;
+using namespace libIRDB;
+
+#include <capstone.h>
+
+
+// static helpers.
+
+
+static uint32_t to_seg_reg_number(const x86_reg &reg)
+{
+	switch(reg)
+	{
+		case X86_REG_ES: return 0;
+		case X86_REG_CS: return 1;
+		case X86_REG_SS: return 2;
+		case X86_REG_DS: return 3;
+		case X86_REG_FS: return 4;
+		case X86_REG_GS: return 5;
+		default: break;
+	}
+	assert(0);
+}
+
+static uint32_t to_reg_number(const x86_reg &reg)
+{
+	switch(reg)
+	{	
+		case X86_REG_AH: 
+		case X86_REG_AL: 
+		case X86_REG_AX: 
+		case X86_REG_EAX: 
+		case X86_REG_RAX:	
+			return 0;
+
+		case X86_REG_CH:
+		case X86_REG_CL:
+		case X86_REG_CX: 
+		case X86_REG_ECX: 
+		case X86_REG_RCX: 
+			return 1;
+
+		case X86_REG_DH: 
+		case X86_REG_DX: 
+		case X86_REG_DL: 
+		case X86_REG_EDX: 
+		case X86_REG_RDX:
+			return 2;
+
+		case X86_REG_BH: 
+		case X86_REG_BL:
+		case X86_REG_BX: 
+		case X86_REG_EBX: 
+		case X86_REG_RBX: 
+			return 3;
+
+		case X86_REG_ESP: 
+		case X86_REG_RSP:
+		case X86_REG_SP:
+		case X86_REG_SPL:
+			return 4;
+
+		case X86_REG_BP: 
+		case X86_REG_BPL: 
+		case X86_REG_EBP:
+		case X86_REG_RBP: 
+			return 5;
+
+		case X86_REG_ESI: 
+		case X86_REG_RSI:
+		case X86_REG_SI:
+		case X86_REG_SIL:
+			return 6;
+
+		case X86_REG_DI: 
+		case X86_REG_DIL:
+		case X86_REG_EDI: 
+		case X86_REG_RDI:
+			return 7;
+
+		case X86_REG_R8:
+		case X86_REG_R8B:
+		case X86_REG_R8D:
+		case X86_REG_R8W: 
+			return 8;
+
+		case X86_REG_R9:
+		case X86_REG_R9B:
+		case X86_REG_R9D:
+		case X86_REG_R9W: 
+			return 9;
+
+		case X86_REG_R10:
+		case X86_REG_R10B:
+		case X86_REG_R10D:
+		case X86_REG_R10W:
+			return 10;
+
+		case X86_REG_R11:
+		case X86_REG_R11B:
+		case X86_REG_R11D:
+		case X86_REG_R11W: 
+			return 11;
+
+		case X86_REG_R12:
+		case X86_REG_R12B:
+		case X86_REG_R12D:
+		case X86_REG_R12W: 
+			return 12;
+
+		case X86_REG_R13:
+		case X86_REG_R13B:
+		case X86_REG_R13D:
+		case X86_REG_R13W: 
+			return 13;
+
+		case X86_REG_R14:
+		case X86_REG_R14B:
+		case X86_REG_R14D:
+		case X86_REG_R14W: 
+			return 14;
+
+		case X86_REG_R15:
+		case X86_REG_R15B:
+		case X86_REG_R15D:
+		case X86_REG_R15W:
+			return 15;
+		default: break;
+	}
+	assert(0);
+}
+
+// methods
+
+//DecodedOperandCapstoneX86_t& DecodedOperandCapstoneX86_t::operator=(const DecodedOperandCapstoneX86_t& copy)
+//{
+//	return *this;
+//}
+//
+//DecodedOperandCapstoneX86_t::DecodedOperandCapstoneX86_t(const DecodedOperandCapstoneX86_t& copy)
+//{
+//	*this=copy;
+//}
+
+DecodedOperandCapstoneX86_t::DecodedOperandCapstoneX86_t( const shared_ptr<void> & p_my_insn, uint8_t p_op_num)
+	:
+	my_insn(p_my_insn),
+	op_num(p_op_num)
+{
+	
+}
+
+DecodedOperandCapstoneX86_t::~DecodedOperandCapstoneX86_t()
+{
+}
+
+
+bool DecodedOperandCapstoneX86_t::isConstant() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+
+	return op.type==X86_OP_IMM;
+}
+
+uint64_t DecodedOperandCapstoneX86_t::getConstant() const
+{
+	if(!isConstant()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-constant operand");
+	
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return op.imm;
+}
+
+string DecodedOperandCapstoneX86_t::getString() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	const auto handle=DecodedInstructionCapstoneX86_t::cs_handle->getHandle();
+
+	switch(op.type)
+	{
+		case X86_OP_REG: 
+			return string(cs_reg_name(handle, op.reg));
+		case X86_OP_IMM: 
+			return to_string(op.imm);
+		case X86_OP_MEM: 
+		{
+//			if (op.mem.segment != X86_REG_INVALID)
+//				ret_val+=cs_reg_name(handle, op.mem.segment) +"  : " ;
+			if (op.mem.base == X86_REG_RIP)
+			{
+				/* convert pc+disp into disp+insn_size. */
+				return to_string(op.mem.disp+the_insn->size);
+			}
+			else
+			{
+				string ret_val;
+				if (op.mem.base != X86_REG_INVALID)
+					ret_val+=cs_reg_name(handle, op.mem.base);
+
+				if (op.mem.index != X86_REG_INVALID)
+					ret_val+=string(" + ") +cs_reg_name(handle, op.mem.index);
+
+				if (op.mem.scale != 1)
+					ret_val+=string(" * ") + to_string(op.mem.scale);
+
+				if (op.mem.disp != 0)
+					ret_val+=" + "+ to_string(op.mem.disp);
+
+				if(ret_val=="")
+					return "0";
+				
+				return ret_val;
+			}
+			assert(0);
+		}
+		case X86_OP_INVALID: 
+		default:
+			assert(0);
+	}
+}
+
+bool DecodedOperandCapstoneX86_t::isRegister() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return op.type==X86_OP_REG;
+}
+
+bool DecodedOperandCapstoneX86_t::isGeneralPurposeRegister() const
+{
+
+	const auto gp_regs=set<x86_reg>({
+		X86_REG_AH, X86_REG_AL, X86_REG_AX, X86_REG_BH, X86_REG_BL,
+		X86_REG_BP, X86_REG_BPL, X86_REG_BX, X86_REG_CH, X86_REG_CL,
+		X86_REG_CX, X86_REG_DH, X86_REG_DI, X86_REG_DIL,
+		X86_REG_DL, X86_REG_DX, X86_REG_EAX, X86_REG_EBP,
+		X86_REG_EBX, X86_REG_ECX, X86_REG_EDI, X86_REG_EDX, 
+		X86_REG_ESI, X86_REG_ESP, X86_REG_RAX,
+		X86_REG_RBP, X86_REG_RBX, X86_REG_RCX, X86_REG_RDI, X86_REG_RDX,
+		X86_REG_RSI, X86_REG_RSP, X86_REG_SI,
+		X86_REG_SIL, X86_REG_SP, X86_REG_SPL, 
+		X86_REG_R8, X86_REG_R9, X86_REG_R10, X86_REG_R11,
+		X86_REG_R12, X86_REG_R13, X86_REG_R14, X86_REG_R15,
+		X86_REG_R8B, X86_REG_R9B, X86_REG_R10B, X86_REG_R11B,
+		X86_REG_R12B, X86_REG_R13B, X86_REG_R14B, X86_REG_R15B, X86_REG_R8D,
+		X86_REG_R9D, X86_REG_R10D, X86_REG_R11D, X86_REG_R12D, X86_REG_R13D,
+		X86_REG_R14D, X86_REG_R15D, X86_REG_R8W, X86_REG_R9W, X86_REG_R10W,
+		X86_REG_R11W, X86_REG_R12W, X86_REG_R13W, X86_REG_R14W, X86_REG_R15W
+		});
+
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  gp_regs.find(op.reg)!=end(gp_regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isMmxRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_MM0, X86_REG_MM1,
+		X86_REG_MM2, X86_REG_MM3, X86_REG_MM4, X86_REG_MM5, X86_REG_MM6,
+		X86_REG_MM7, X86_REG_R8});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isFpuRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_ST0, X86_REG_ST1, X86_REG_ST2, X86_REG_ST3,
+		X86_REG_ST4, X86_REG_ST5, X86_REG_ST6, X86_REG_ST7,
+		});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isSseRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_XMM0, X86_REG_XMM1, X86_REG_XMM2, X86_REG_XMM3, X86_REG_XMM4,
+		X86_REG_XMM5, X86_REG_XMM6, X86_REG_XMM7, X86_REG_XMM8, X86_REG_XMM9,
+		X86_REG_XMM10, X86_REG_XMM11, X86_REG_XMM12, X86_REG_XMM13, X86_REG_XMM14,
+		X86_REG_XMM15, X86_REG_XMM16, X86_REG_XMM17, X86_REG_XMM18, X86_REG_XMM19,
+		X86_REG_XMM20, X86_REG_XMM21, X86_REG_XMM22, X86_REG_XMM23, X86_REG_XMM24,
+		X86_REG_XMM25, X86_REG_XMM26, X86_REG_XMM27, X86_REG_XMM28, X86_REG_XMM29,
+		X86_REG_XMM30, X86_REG_XMM31
+		});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isAvxRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_YMM0, X86_REG_YMM1, X86_REG_YMM2,
+		X86_REG_YMM3, X86_REG_YMM4, X86_REG_YMM5, X86_REG_YMM6, X86_REG_YMM7,
+		X86_REG_YMM8, X86_REG_YMM9, X86_REG_YMM10, X86_REG_YMM11, X86_REG_YMM12,
+		X86_REG_YMM13, X86_REG_YMM14, X86_REG_YMM15, X86_REG_YMM16, X86_REG_YMM17,
+		X86_REG_YMM18, X86_REG_YMM19, X86_REG_YMM20, X86_REG_YMM21, X86_REG_YMM22,
+		X86_REG_YMM23, X86_REG_YMM24, X86_REG_YMM25, X86_REG_YMM26, X86_REG_YMM27,
+		X86_REG_YMM28, X86_REG_YMM29, X86_REG_YMM30, X86_REG_YMM31,
+		});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isZmmRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_ZMM0, X86_REG_ZMM1, X86_REG_ZMM2,
+		X86_REG_ZMM3, X86_REG_ZMM4, X86_REG_ZMM5, X86_REG_ZMM6, X86_REG_ZMM7,
+		X86_REG_ZMM8, X86_REG_ZMM9, X86_REG_ZMM10, X86_REG_ZMM11, X86_REG_ZMM12,
+		X86_REG_ZMM13, X86_REG_ZMM14, X86_REG_ZMM15, X86_REG_ZMM16, X86_REG_ZMM17,
+		X86_REG_ZMM18, X86_REG_ZMM19, X86_REG_ZMM20, X86_REG_ZMM21, X86_REG_ZMM22,
+		X86_REG_ZMM23, X86_REG_ZMM24, X86_REG_ZMM25, X86_REG_ZMM26, X86_REG_ZMM27,
+		X86_REG_ZMM28, X86_REG_ZMM29, X86_REG_ZMM30, X86_REG_ZMM31,
+		});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isSpecialRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_CR1, X86_REG_CR2, X86_REG_CR3, X86_REG_CR4, X86_REG_CR5,
+		X86_REG_CR6, X86_REG_CR7, X86_REG_CR8, X86_REG_CR9, X86_REG_CR10,
+        	X86_REG_CR11, X86_REG_CR12, X86_REG_CR13, X86_REG_CR14, X86_REG_CR15,
+		X86_REG_DR0, X86_REG_DR1, X86_REG_DR2, X86_REG_DR3, X86_REG_DR4,
+        	X86_REG_DR5, X86_REG_DR6, X86_REG_DR7,
+		});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+bool DecodedOperandCapstoneX86_t::isSegmentRegister() const
+{
+	const auto regs=set<x86_reg>({
+		X86_REG_CS,
+		X86_REG_DS,
+		X86_REG_ES,
+		X86_REG_FS,
+		X86_REG_GS,
+
+		});
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isRegister() &&  regs.find(op.reg)!=end(regs);
+}
+
+
+
+uint32_t DecodedOperandCapstoneX86_t::getRegNumber() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	if(isGeneralPurposeRegister())
+		return to_reg_number(op.reg);
+	else if(isMmxRegister())
+		return op.reg-X86_REG_MM0;
+	else if(isFpuRegister())
+		return op.reg-X86_REG_ST0;
+	else if(isSseRegister())
+		return op.reg-X86_REG_XMM0;
+	else if(isAvxRegister())
+		return op.reg-X86_REG_YMM0;
+	else if(isZmmRegister())
+		return op.reg-X86_REG_ZMM0;
+	else if(isSegmentRegister())
+		return to_seg_reg_number(op.reg);
+	else
+		assert(0);
+}
+
+bool DecodedOperandCapstoneX86_t::isMemory() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return op.type==X86_OP_MEM;
+}
+
+bool DecodedOperandCapstoneX86_t::hasBaseRegister() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isMemory() && op.mem.base!=X86_REG_INVALID && op.mem.base!=X86_REG_RIP;
+}
+
+bool DecodedOperandCapstoneX86_t::hasIndexRegister() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isMemory() && op.mem.index!=X86_REG_INVALID;
+}
+
+uint32_t DecodedOperandCapstoneX86_t::getBaseRegister() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return to_reg_number((x86_reg)op.mem.base);
+}
+
+uint32_t DecodedOperandCapstoneX86_t::getIndexRegister() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return to_reg_number((x86_reg)op.mem.index);
+}
+
+uint32_t DecodedOperandCapstoneX86_t::getScaleValue() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return op.mem.scale;
+}
+
+bool DecodedOperandCapstoneX86_t::hasMemoryDisplacement() const
+{
+
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+
+	const auto the_insn = static_cast<cs_insn*>(my_insn.get());
+	//const auto &op = (the_insn->detail->x86.operands[op_num]);
+
+	const auto modrm = the_insn->detail->x86.modrm;
+	const auto mod = (modrm >> 6) & 0x3;
+	const auto rm = (modrm & 0x7);
+	const auto sib = the_insn->detail->x86.sib;
+	const auto sib_base = (sib >> 0) & 0x7;
+	//const auto sib_index = (sib >> 3) & 0x7;
+
+	switch (mod)
+	{
+		case 0 /* 00 */:
+			if (rm == 4 &&	 // indicates SIB is present.
+			    sib_base == 0x5 // indicates disp32 when sib present and mod=00.
+			   )
+				return true;	// abs 32-bit
+
+			if (rm == 5)
+				return true;	// pcrel or abs 32-bit depending on if 32-bit or 64-bit arch.
+
+			return false;
+
+		case 1 /* 01 */:
+			return true;
+
+		case 2 /* 10 */:
+			return true;
+
+		case 3 /* 11 */:
+			return false;
+
+		default: 
+			assert(0); //unreachable
+	}
+	assert(0); // unreachable
+} // end of DecodedOperandCapstoneX86_t::hasMemoryDisplacement()
+
+virtual_offset_t DecodedOperandCapstoneX86_t::getMemoryDisplacement() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return op.mem.disp;
+}
+
+bool DecodedOperandCapstoneX86_t::isPcrel() const
+{
+	if(!isMemory())	return false;
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+ 
+	return (op.mem.base==X86_REG_RIP || op.mem.base==X86_REG_EIP || op.mem.base==X86_REG_IP);
+}
+
+/* in bytes */
+uint32_t DecodedOperandCapstoneX86_t::getMemoryDisplacementEncodingSize() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of non-memory operand");
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        //const auto &op = (the_insn->detail->x86.operands[op_num]);
+
+	const auto modrm=the_insn->detail->x86.modrm;
+	const auto mod=(modrm>>6)&0x3;
+	const auto rm=(modrm)&0x7;
+	const auto sib=the_insn->detail->x86.sib;
+	const auto sib_base=(sib>>0)&0x7;
+	//const auto sib_index=(sib>>3)&0x7;
+
+	switch(mod)
+	{
+		case 0 /* 00 */:  	
+			if(rm==4 &&	 // indicates SIB is present.
+			   sib_base==0x5 // indicates disp32 when sib present and mod=00.
+			  ) 
+				return 4;	// abs 32-bit
+				
+			if(rm==5)
+				return 4;	// pcrel or abs 32-bit depending on if 32-bit or 64-bit arch.
+
+			throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of operand without displacement");
+
+		case 1 /* 01 */: 	return 1;
+		case 2 /* 10 */: 	return 4;
+
+		case 3 /* 11 */:
+			throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of operand without displacement");
+		default: assert(0);
+	}
+	assert(0);
+}
+
+uint32_t DecodedOperandCapstoneX86_t::getArgumentSizeInBytes() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return op.size;
+}
+
+uint32_t DecodedOperandCapstoneX86_t::getArgumentSizeInBits() const
+{
+	return getArgumentSizeInBytes()*8;
+}
+
+bool DecodedOperandCapstoneX86_t::hasSegmentRegister() const
+{
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return isMemory() && (op.mem.segment != X86_REG_INVALID);
+
+}
+
+uint32_t DecodedOperandCapstoneX86_t::getSegmentRegister() const
+{
+	if(!isMemory()) throw std::logic_error(string("Cannot ")+__FUNCTION__+"  of operand without memory operand");
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return to_seg_reg_number((x86_reg)op.mem.segment);
+}
+
+
+set<string> write_only_operand_mnemonics=
+ 	{
+		"seta",
+		"setae",
+		"setb",
+		"setbe",
+		"setc",
+		"sete",
+		"setg",
+		"setge",
+		"setl",
+		"setle",
+		"setna",
+		"setnae",
+		"setnb",
+		"setnbe",
+		"setnc",
+		"setne",
+		"setng",
+		"setnge",
+		"setnl",
+		"setnle",
+		"setno",
+		"setnp",
+		"setns",
+		"setnz",
+		"seto",
+		"setp",
+		"setpe",
+		"setpo",
+		"sets",
+		"setz",
+		"fst",
+		"fstp",
+		"fist",
+		"fistp"
+	};
+
+set<string> write_first_operand_mnemonics=
+	{
+		"movups",
+      "movd",
+		"rol",
+      "movdqa",
+		"ror",
+      "movdqu",
+      "movq"
+	};
+
+set<string> read_only_operand_mnemonics=
+	{
+		// specal read-only op cases, rest are some form of compare.
+		"push",
+
+		// test 
+		"test",
+
+		// bit test (but not bt+comp or bt+reset as those have a reg dest.
+		"bt",
+
+		// compare 
+		"cmp",
+
+		// multiplies and divides implicitly read/write eax/ax instead of op0 
+		"mul",
+		// "imul", imul has 2 forms, have to handle separately.
+		"div",
+		"idiv",
+
+		// compare string
+		"cmps",
+		"cmpsb",
+		"cmpsw",
+		"cmpsd",
+		"cmpsq",
+
+		// float compare [and pop]
+		"fcom",
+		"fcomp",
+		"fcompp",
+
+		// compare floating point values
+		"fcomi",
+		"fcomip",
+		"fucomi",
+		"fucomip",
+
+
+		// logical compare
+		"ptest",
+		"vptest",
+
+		// scas variants
+		"scas",
+		"scass",
+		"scasb",
+		"scasw",
+		"scasd",
+
+		// ucomiss -- unordered cmpare scalar single-precision floating-point values and set flags
+		"ucomiss",
+		"vucomiss",
+
+		// comiss -- unordered cmpare scalar single-precision floating-point values and set flags
+		"comiss",
+		"vcomiss",
+
+		// comisd "comapre scalar ordered double-preicions floating-point values and set flags
+		"comisd",
+		"vcomisd",
+
+		// ucomisd "comapre scalar ordered double-preicions floating-point values and set flags
+		"ucomisd",
+		"vucomisd",
+
+		// packed bit test
+		"vtestps",
+		"vtestpd"
+
+		// compare packed {double,single}-prec float values 
+		"cmppd",
+		"vcmppd",
+		"cmpps",
+		"vcmpps",
+
+		// compare sclar {double,single}-prec float values
+		"cmpsd",
+		"vcmpsd",
+		"cmpss",
+		"vcmpss",
+
+		// compare packed data for equal
+		"pcmpeqb",
+		"vpcmpeqb",
+		"pcmpeqw",
+		"vpcmpeqw",
+		"pcmpeqd",
+		"vpcmpeqd",
+		"pcmpeqq",
+		"vpcmpeqq",
+
+		// packed compare explicit length string, return {index, mask}
+		"pcmpestri",
+		"vpcmpestri",
+		"pcmpestrm",
+		"vpcmpestrm",
+
+		// compare packed data for greather than
+		"pcompgtb",
+		"vpcompgtb",
+		"pcompgtw",
+		"vpcompgtw",
+		"pcompgtd",
+		"vpcompgtd",
+		"pcompgtq",
+		"vpcompgtq",
+
+		// packed compare implicit length string, return index or mask
+		"pcmpistri",
+		"vpcmpistri",
+		"pcmpistrm",
+		"vpcmpistrm",
+
+		// test if in transactional region
+		"xtest",
+
+	};
+
+
+
+bool DecodedOperandCapstoneX86_t::isRead() const
+{
+	if(!isWritten())
+		return true;
+
+	const auto d=DecodedInstructionCapstoneX86_t(my_insn);
+	const auto d_mnemonic=d.getMnemonic();
+	const auto woom_it=write_only_operand_mnemonics.find(d_mnemonic);
+	const auto in_woom=(woom_it!=end(write_only_operand_mnemonics));
+	if(in_woom)
+		return false;
+		
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return (op.access & CS_AC_READ)!=0;
+/*
+	if(op_num!=0)
+		return true;
+
+	const auto d=DecodedInstructionCapstoneX86_t(my_insn);
+	if(d.isBranch())	
+		return true;	
+
+	const auto room_it=read_only_operand_mnemonics.find(d.getMnemonic());
+	const auto in_room=(room_it!=end(read_only_operand_mnemonics));
+	if(in_room)
+		return true;
+
+	if(d.getMnemonic().substr(0,3)=="mov")
+		return false;
+
+	// op0 is typically read/write
+	return true;
+
+	assert(0);
+*/
+}
+
+bool DecodedOperandCapstoneX86_t::isWritten() const
+{	
+	const auto d=DecodedInstructionCapstoneX86_t(my_insn);
+	const auto d_mnemonic=d.getMnemonic();
+
+	// special case check:  all operands are reads
+	const auto room_it=read_only_operand_mnemonics.find(d_mnemonic);
+	const auto in_room=(room_it!=end(read_only_operand_mnemonics));
+	if(in_room)
+		return false;
+
+	// special case check:  all operands are writes
+	const auto woom_it=write_only_operand_mnemonics.find(d_mnemonic);
+	const auto in_woom=(woom_it!=end(write_only_operand_mnemonics));
+	if(in_woom)
+		return true;
+
+	// special case check:  first operand is writes
+	if(op_num==0)
+	{
+		const auto wfom_it=write_first_operand_mnemonics.find(d_mnemonic);
+		const auto in_wfom=(wfom_it!=end(write_first_operand_mnemonics));
+		if(in_wfom)
+			return true;
+	}
+
+	// special case of imul
+	// imul has a 1-argument form which uses all it's operands
+	if(d_mnemonic=="imul" && !d.hasOperand(1))
+		return false;
+
+
+	// default: use capstone's advice.
+        const auto the_insn=static_cast<cs_insn*>(my_insn.get());
+        const auto &op = (the_insn->detail->x86.operands[op_num]);
+	return (op.access & CS_AC_WRITE)!=0;
+/*
+	if(op_num!=0)
+		return false;
+	const auto d=DecodedInstructionCapstoneX86_t(my_insn);
+	if(d.isBranch())	
+		return false;	
+
+	const auto room_it=read_only_operand_mnemonics.find(d.getMnemonic());
+	const auto in_room=(room_it!=end(read_only_operand_mnemonics));
+	if(in_room)
+		return false;
+
+	return true;
+*/
+}
diff --git a/irdb-lib/libIRDB-core/src/operand_dispatch.cpp b/irdb-lib/libIRDB-core/src/operand_dispatch.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0790f4677cdeb2637ee5ce37efe3a3df004b59c5
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/operand_dispatch.cpp
@@ -0,0 +1,64 @@
+
+#include <libIRDB-core.hpp>
+#include <operand_csx86.hpp>
+#include <decode_csx86.hpp>
+#include <operand_dispatch.hpp>
+#include <decode_dispatch.hpp>
+
+using namespace std;
+using namespace libIRDB;
+
+DecodedOperandDispatcher_t::DecodedOperandDispatcher_t(const shared_ptr<DecodedOperandCapstone_t> copy_cs)  
+{
+	cs=copy_cs;
+} 
+
+DecodedOperandDispatcher_t::DecodedOperandDispatcher_t(const DecodedOperandDispatcher_t& copy) 
+{
+	cs=copy.cs;
+}
+
+DecodedOperandDispatcher_t::~DecodedOperandDispatcher_t()
+{
+}
+
+DecodedOperandDispatcher_t& DecodedOperandDispatcher_t::operator=(const DecodedOperandDispatcher_t& copy)
+{
+	cs=copy.cs;
+	return *this;
+}
+
+#define passthrough_to_cs(ret_type, method_name) \
+	ret_type DecodedOperandDispatcher_t::method_name() const \
+	{ \
+		return cs->method_name(); \
+	} 
+
+passthrough_to_cs(bool, isConstant);
+passthrough_to_cs(uint64_t, getConstant);
+passthrough_to_cs(string, getString);
+passthrough_to_cs(bool, isRegister);
+passthrough_to_cs(bool, isGeneralPurposeRegister);
+passthrough_to_cs(bool, isMmxRegister);
+passthrough_to_cs(bool, isFpuRegister);
+passthrough_to_cs(bool, isSseRegister);
+passthrough_to_cs(bool, isAvxRegister);
+passthrough_to_cs(bool, isSpecialRegister);
+passthrough_to_cs(bool, isSegmentRegister);
+passthrough_to_cs(uint32_t, getRegNumber);
+passthrough_to_cs(bool, isMemory);
+passthrough_to_cs(bool, hasBaseRegister);
+passthrough_to_cs(bool, hasIndexRegister);
+passthrough_to_cs(uint32_t, getBaseRegister);
+passthrough_to_cs(uint32_t, getIndexRegister);
+passthrough_to_cs(uint32_t, getScaleValue);
+passthrough_to_cs(bool, hasMemoryDisplacement);
+passthrough_to_cs(virtual_offset_t, getMemoryDisplacement);
+passthrough_to_cs(bool, isPcrel);
+passthrough_to_cs(uint32_t, getMemoryDisplacementEncodingSize);
+passthrough_to_cs(uint32_t, getArgumentSizeInBytes);
+passthrough_to_cs(uint32_t, getArgumentSizeInBits);
+passthrough_to_cs(bool, hasSegmentRegister);
+passthrough_to_cs(uint32_t, getSegmentRegister);
+passthrough_to_cs(bool, isRead);
+passthrough_to_cs(bool, isWritten);
diff --git a/irdb-lib/libIRDB-core/src/pqxxdb.cpp b/irdb-lib/libIRDB-core/src/pqxxdb.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..37fa2e986e477755c5b39590eb26cfad403f6fbf
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/pqxxdb.cpp
@@ -0,0 +1,77 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <all.hpp>
+#include <pqxx/pqxx>
+#include <string>
+
+using namespace libIRDB;
+using namespace std;
+
+pqxxDB_t::pqxxDB_t() : DBinterface_t(), txn(conn)
+{
+	/* no other init needed */
+}
+
+void pqxxDB_t::issueQuery(std::string query)
+{
+	results=txn.exec(query);
+	results_iter=results.begin();
+}
+
+void pqxxDB_t::issueQuery(std::stringstream & query)
+{
+	results=txn.exec(query);
+	results_iter=results.begin();
+}
+
+void pqxxDB_t::moveToNextRow()
+{
+	assert(!isDone());
+	++results_iter;
+}
+
+std::string pqxxDB_t::getResultColumn(std::string colname)
+{
+	if(results_iter[colname].is_null())
+		return std::string("");
+
+	pqxx::binarystring bin_str(results_iter.at(colname));
+
+	return bin_str.str();
+
+//	return results_iter[colname].as<std::string>();
+}
+
+bool pqxxDB_t::isDone()
+{
+	return results_iter==results.end();
+}
+
+void pqxxDB_t::commit()
+{
+	txn.commit();
+}
+
+unique_ptr<IRDB_SDK::pqxxDB_t> IRDB_SDK::pqxxDB_t::factory()
+{
+	return unique_ptr<IRDB_SDK::pqxxDB_t>(new libIRDB::pqxxDB_t);
+}
diff --git a/irdb-lib/libIRDB-core/src/reloc.cpp b/irdb-lib/libIRDB-core/src/reloc.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..dac3a40c8a3f6cb214501f89280d4e88510c4705
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/reloc.cpp
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <all.hpp>
+#include <irdb-util>
+
+using namespace std;
+
+vector<std::string> Relocation_t::WriteToDB(File_t* fid, BaseObj_t* myinsn)
+{
+        db_id_t wrt_id=wrt_obj ? wrt_obj->getBaseID() : BaseObj_t::NOT_IN_DATABASE;
+/*
+        string q;
+        q ="insert into " + fid->relocs_table_name;
+        q+="(reloc_id,reloc_offset,reloc_type,instruction_id,addend,wrt_id,doip_id) "+
+                string(" VALUES (") +
+*/
+	return {
+                to_string(getBaseID()),
+                to_string(offset),
+                (type),
+                to_string(myinsn->getBaseID()),
+                to_string(addend),
+                to_string(wrt_id),
+                to_string(getDoipID())
+		};
+}
+
diff --git a/irdb-lib/libIRDB-core/src/scoop.cpp b/irdb-lib/libIRDB-core/src/scoop.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ff6512a9eab76f8e43ad4511197f1e5b623c2606
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/scoop.cpp
@@ -0,0 +1,103 @@
+#include "all.hpp"
+#include <irdb-util>
+#include <sstream>
+#include <iomanip>
+
+
+using namespace std;
+using namespace libIRDB;
+
+
+#define SCOOP_THRESHOLD 990000000	 /* almost 1gb -- leaving a bit of head room for overhead sql syntax overheads */
+#define SCOOP_CHUNK_SIZE (10*1024*1024)	 /* 10 mb  */
+
+//#define SCOOP_THRESHOLD 10	 /* almost 1gb -- leaving a bit of head room for overhead sql syntax overheads */
+//#define SCOOP_CHUNK_SIZE (128)
+
+string DataScoop_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	string q= ""; 
+	    
+	if(contents.length() < SCOOP_THRESHOLD)
+		q+=WriteToDBRange(fid,newid, 0,  contents.length(), fid->scoop_table_name);
+	else
+	{
+		q+=WriteToDBRange(fid,newid, 0,  SCOOP_THRESHOLD, fid->scoop_table_name);
+		q+=WriteToDBRange(fid,newid , SCOOP_THRESHOLD,  contents.length(), fid->scoop_table_name+"_part2");
+	}
+
+	return q;
+}
+
+string DataScoop_t::WriteToDBRange(File_t *fid, db_id_t newid, int start, int end, string table_name)
+{
+
+/*
+  scoop_id           SERIAL PRIMARY KEY,        -- key
+  name               text DEFAULT '',           -- string representation of the type
+  type_id            integer,                   -- the type of the data, as an index into the table table.
+  start_address_id   integer,                   -- address id for start.
+  end_address_id     integer,                   -- address id for end
+  permissions        integer                    -- in umask format (bitmask for rwx)
+
+ */
+
+	db_id_t type_id=(getType() ? getType()->getBaseID() : BaseObj_t::NOT_IN_DATABASE);
+
+        ostringstream hex_data;
+
+
+        string q=string("insert into ")+table_name+
+                string(" (scoop_id, name, type_id, start_address_id, end_address_id, data, permissions, relro) ")+
+                string(" VALUES (") +
+                string("'") + to_string(getBaseID()) + string("', ") +
+                string("'") + getName()  + string("', ") +
+                string("'") + to_string(type_id) + string("', ") +
+                string("'") + to_string(getStart()->getBaseID()) + string("', ") +
+                string("'") + to_string(getEnd()->getBaseID()) + string("', ") +
+                string("'") + /* empty data field -- for now  + */ string("', ") +
+                string("'") + to_string(permissions) + string("', ") + 
+                string("'") + to_string(is_relro) + string("'); ") ;
+	// add the table row with empty data field.
+	dbintr->issueQuery(q);
+
+
+	// now try to append the data to the field in chunks.
+
+	string query_start="update "+table_name+" set data = data || decode('";
+	string query_end="', 'hex') where scoop_id="+ string("'") + to_string(getBaseID()) + string("'; ") ;
+
+
+        hex_data << query_start << setfill('0') << hex;
+        for (auto i = start; i < end; ++i)
+	{
+                hex_data << setw(2) << (int)(contents[i]&0xff);
+
+		stringstream::pos_type offset = hex_data.tellp();
+
+		if(offset > SCOOP_CHUNK_SIZE)
+		{
+			// q+=hex_data.str();
+			// hex_data.str("");	// reset to empty
+			// hex_data.clear();
+
+			// tag the end,
+			hex_data << query_end;
+
+			// append this chunk to the db.
+			dbintr->issueQuery(hex_data.str());
+
+			// restart 
+			hex_data.str("");	// reset to empty
+			hex_data.clear();
+        		hex_data << query_start << setfill('0') << hex;
+		}
+	}
+	hex_data << query_end;
+
+	// append this chunk to the db.
+	dbintr->issueQuery(hex_data.str());
+
+	return "";
+}
+
diff --git a/irdb-lib/libIRDB-core/src/type.cpp b/irdb-lib/libIRDB-core/src/type.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..67ceb48b61da9637c3012b9ec8424e667af0007a
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/type.cpp
@@ -0,0 +1,143 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include "all.hpp" 
+#include <irdb-util>
+
+using namespace std;
+using namespace libIRDB;
+
+bool BasicType_t::isNumericType() const
+{
+		auto type = getTypeID();
+		return type == IRDB_SDK::itNumeric || 
+		       type == IRDB_SDK::itInt     || 
+		       type == IRDB_SDK::itFloat   || 
+		       type == IRDB_SDK::itDouble  || 
+		       type == IRDB_SDK::itChar;
+}
+
+/*
+CREATE TABLE #TYP#
+(
+  type_id            integer,     
+  type               integer DEFAULT 0,    -- possible types (0: UNKNOWN)
+  name               text DEFAULT '',      -- string representation of the type
+  ref_type_id        integer DEFAULT -1,   -- for aggregate types
+  pos                integer DEFAULT -1,   -- for aggregate types, position in aggregate
+  ref_type_id2       integer DEFAULT -1,   -- for func types
+  doip_id            integer DEFAULT -1    -- the DOIP
+);
+*/
+
+string BasicType_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	assert(fid);
+
+	string q=string("insert into ")+fid->types_table_name + 
+		string(" (type_id, type, name, ref_type_id, pos, ref_type_id2) ")+
+		string(" VALUES (") + 
+		string("'") + to_string(getBaseID()) + string("', ") + 
+		string("'") + to_string(getTypeID()) + string("', ") + 
+		string("'") + getName()              + string("','-1','-1','-1') ; ") ;
+
+//    cout << "BasicType_t::WriteToDB(): " << q << endl;
+	return q;
+}
+
+string PointerType_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	assert(fid && getReferentType());
+	string q=string("insert into ")+fid->types_table_name + 
+		string(" (type_id, type, name, ref_type_id,pos,ref_type_id2) ")+
+		string(" VALUES (") + 
+		string("'") + to_string(getBaseID())                    + string("', ") + 
+		string("'") + to_string(getTypeID())                    + string("', ") + 
+		string("'") + getName()                                 + string("', ") +
+		string("'") + to_string(getReferentType()->getBaseID()) + 
+		string("','-1','-1') ; ") ;
+
+//    cout << "PointerType_t::WriteToDB(): " << q << endl;
+	return q;
+}
+
+string AggregateType_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	assert(fid);
+	assert(getNumAggregatedTypes() > 0);
+
+	string q;
+
+	for (auto i = 0U; i < getNumAggregatedTypes(); ++i)
+	{
+		auto t = getAggregatedType(i);
+		q+=string("insert into ")+fid->types_table_name + 
+			string(" (type_id, type, name, ref_type_id, pos,ref_type_id2) ")+
+			string(" VALUES (") + 
+			string("'") + to_string(getBaseID())                    + string("', ") + 
+			string("'") + to_string(getTypeID())                    + string("', ") + 
+			string("'") + getName()                                 + string("', ") +
+			string("'") + to_string(t->getBaseID()) + string("', ") +
+			string("'") + to_string(i) +
+			string("','-1') ; ") ;
+	}
+
+ //   cout << "AggregatedType_t::WriteToDB(): " << q << endl;
+	return q;
+}
+
+void AggregateType_t::addAggregatedType(IRDB_SDK::Type_t *t, int pos)
+{
+	refTypes.push_back(t);
+
+//	cout << "AggregatedType_t::AddAggregatedType(): new size: " << refTypes.size() << endl;
+}
+
+/*
+CREATE TABLE #TYP#
+(
+  type_id            integer,     
+  type               integer DEFAULT 0,    -- possible types (0: UNKNOWN)
+  name               text DEFAULT '',      -- string representation of the type
+  ref_type_id        integer DEFAULT -1,   -- for aggregate types
+  pos                integer DEFAULT -1,   -- for aggregate types, position in aggregate
+  ref_type_id2       integer DEFAULT -1,   -- for func types
+  doip_id            integer DEFAULT -1    -- the DOIP
+);
+*/
+string FuncType_t::WriteToDB(File_t *fid, db_id_t newid)
+{
+	assert(fid);
+	assert(getReturnType());
+	assert(getArgumentsType());
+	string q=string("insert into ")+fid->types_table_name + 
+		string(" (type_id, type, name, ref_type_id, ref_type_id2,pos) ")+
+		string(" VALUES (") + 
+		string("'") + to_string(getBaseID())                    + string("', ") + 
+		string("'") + to_string(getTypeID())                    + string("', ") + 
+		string("'") + getName()                                 + string("', ") +
+		string("'") + to_string(getReturnType()->getBaseID()) + string("', ") +
+		string("'") + to_string(getArgumentsType()->getBaseID()) + 
+		string("','-1') ; ") ;
+
+//  cout << "FuncType_t::WriteToDB(): " << q << endl;
+	return q;
+}
+
diff --git a/irdb-lib/libIRDB-core/src/variantid.cpp b/irdb-lib/libIRDB-core/src/variantid.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..fc33c6ed9434e96cab9d5383315dacfb67a8e681
--- /dev/null
+++ b/irdb-lib/libIRDB-core/src/variantid.cpp
@@ -0,0 +1,514 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+
+#include <all.hpp>
+#include <irdb-util>
+#include <stdlib.h>
+using namespace std;
+
+template <class T>
+inline string to_string (const T& t)
+{
+	stringstream ss;
+	ss << t;
+	return ss.str();
+}
+
+
+
+/*
+ * Create a new variant ID that is not yet in the database
+ */
+VariantID_t::VariantID_t() :
+	BaseObj_t(NULL)
+{
+        schema_ver=CURRENT_SCHEMA;
+        orig_pid=-1;       
+        name="";
+}
+
+
+VariantID_t::~VariantID_t()
+{
+	for(auto it : files)	
+	{
+		delete it;
+	}
+}
+
+
+void VariantID_t::CreateTables()
+{
+	// note:  this tables are now part of File_t.
+	assert(0);
+}
+
+VariantID_t::VariantID_t(db_id_t pid) : BaseObj_t(NULL)
+{
+	std::string q="select * from Variant_info where variant_id = " ;
+	q+=to_string(pid);
+	q+=";";
+
+       	try 
+	{
+		BaseObj_t::dbintr->issueQuery(q);
+	}
+	catch (const std::exception &e)
+	{
+        	schema_ver=-1;
+        	orig_pid=-1;       
+        	name="";
+
+		throw DatabaseError_t(DatabaseError_t::VariantTableNotRegistered); 
+	};
+	
+	if(BaseObj_t::dbintr->isDone())
+		throw DatabaseError_t(DatabaseError_t::VariantNotInDatabase); 
+
+        setBaseID(atoi(BaseObj_t::dbintr->getResultColumn("variant_id").c_str()));
+        schema_ver=atoi(BaseObj_t::dbintr->getResultColumn("schema_version_id").c_str());
+        orig_pid=atoi(BaseObj_t::dbintr->getResultColumn("orig_variant_id").c_str());
+        name=(BaseObj_t::dbintr->getResultColumn("name"));
+
+
+	BaseObj_t::dbintr->moveToNextRow();
+	assert(BaseObj_t::dbintr->isDone());
+
+        ReadFilesFromDB();
+}
+
+bool VariantID_t::isRegistered() const
+{
+	return getBaseID()!=BaseObj_t::NOT_IN_DATABASE;
+}
+
+bool VariantID_t::registerID()
+{
+	assert(!isRegistered());
+
+	std::string q;
+	q="insert into variant_info (schema_version_id,name) "
+		"values('";
+	q+=to_string(schema_ver);
+	q+="','";
+	q+=to_string(name);
+	q+="')";
+	q+="returning variant_id;";
+
+	dbintr->issueQuery(q);
+	assert(!BaseObj_t::dbintr->isDone());
+
+	db_id_t newid=atoi(dbintr->getResultColumn("variant_id").c_str());
+
+	/* set IDs */
+	setBaseID(newid);
+	if(NOT_IN_DATABASE==orig_pid)
+		orig_pid=newid;
+
+	BaseObj_t::dbintr->moveToNextRow();
+	assert(BaseObj_t::dbintr->isDone());
+
+	return true;
+}    
+
+IRDB_SDK::VariantID_t* VariantID_t::clone(bool deep)
+{
+	assert(isRegistered());	// cannot clone something that's not registered 
+
+	// create the new program id 
+	VariantID_t *ret=new VariantID_t;
+	
+	// set the inhereted fields 
+	ret->setName(name+"_cloneof"+to_string(getBaseID()));
+	ret->orig_pid=orig_pid;
+
+	// register the new VID to the database. 
+	ret->registerID();
+	// and write it to the database
+	ret->WriteToDB();
+
+	// (shallow) clone the file_info table entries 
+	std::string q;
+
+	// lastly update the variant_dependency table to make a copy of the rows in which 
+	// the old variant depended upon.  The new rows will indicate that the 
+	// new variant also depends on those files 
+	q="insert into variant_dependency (variant_id, file_id, doip_id) select '";
+	q+=to_string(ret->getBaseID());
+	q+="', file_id, doip_id from variant_dependency where variant_id='";
+	q+=to_string(getBaseID());
+	q+="';";
+	dbintr->issueQuery(q);
+
+	if(deep)
+		ret->CloneFiles(files);
+
+	return ret;
+}       
+
+void VariantID_t::CloneFiles(FileSet_t &files)
+{
+	for(auto fiter=files.begin(); fiter!=files.end(); ++fiter)
+	{
+		auto the_file=dynamic_cast<File_t*>(*fiter);
+		files.insert(CloneFile(the_file));
+	}
+}
+
+File_t* VariantID_t::CloneFile(File_t* fptr)
+{
+	std::string q;
+
+	q ="insert into file_info "
+	    "("
+  	    "orig_file_id," 
+  	    "url," 
+  	    "hash," 
+  	    "arch," 
+  	    "elfoid," 
+  	    "doip_id" 
+	    ") "
+	    "values ( '" + 
+            to_string(fptr->orig_fid) + "', '" +
+            to_string(fptr->url) + "', '" +
+            to_string(fptr->hash) + "', '" +
+            to_string(fptr->arch) + "', '" +
+            to_string(fptr->elfoid) + "', '" +
+            to_string(fptr->getDoipID()) + 
+	    "' ) ";
+	q+=" returning file_id; ";
+
+
+        dbintr->issueQuery(q);
+        assert(!BaseObj_t::dbintr->isDone());
+
+        db_id_t newfid=atoi(dbintr->getResultColumn("file_id").c_str());
+
+	std::string atn="atnfid"+to_string(newfid);
+	std::string ftn="ftnfid"+to_string(newfid);
+	std::string itn="itnfid"+to_string(newfid);
+	std::string icfs="icfsfid"+to_string(newfid);
+	std::string icfsmap="icfsmapfid"+to_string(newfid);
+	std::string rtn="rtnfid"+to_string(newfid);
+	std::string dtn="dtnfid"+to_string(newfid);
+	std::string dtn_part2="dtnfid"+to_string(newfid)+"_part2";
+	std::string typ="typfid"+to_string(newfid);
+	std::string ehp="ehpfid"+to_string(newfid);
+	std::string css="cssfid"+to_string(newfid);
+
+	q ="update file_info set address_table_name='"+atn;
+	q+="', function_table_name='"+ftn;
+	q+="', instruction_table_name='"+itn;
+	q+="', icfs_table_name='"+icfs;
+	q+="', icfs_map_table_name='"+icfsmap;
+	q+="', relocs_table_name='"+rtn;
+	q+="', types_table_name='"+typ;
+	q+="', scoop_table_name='"+dtn;
+	q+="', ehpgm_table_name='"+ehp;
+	q+="', ehcss_table_name='"+css;
+	q+="' where file_id='";
+	q+=to_string(newfid);
+	q+="' ; ";
+	
+        dbintr->issueQuery(q);
+
+	File_t* newfile=new File_t(newfid, fptr->orig_fid, fptr->url, fptr->hash, fptr->arch, 
+		fptr->elfoid, atn, ftn, itn, icfs, icfsmap, rtn, typ, dtn, ehp, css, fptr->getDoipID());
+
+	newfile->CreateTables();
+
+        // first drop the old values
+        q="drop table ";
+        q+=itn;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=icfsmap;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=icfs;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=atn;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=ftn;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=rtn;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=typ;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=dtn;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=dtn_part2;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=ehp;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+        q="drop table ";
+        q+=css;
+        q+=" ; ";
+        dbintr->issueQuery(q);
+
+
+        // next issue SQL to clone each table
+        q="select * into ";
+        q+=atn;
+        q+=" from ";
+        q+=fptr->address_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=itn;
+        q+=" from ";
+        q+=fptr->instruction_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=icfs;
+        q+=" from ";
+        q+=fptr->icfs_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=icfsmap;
+        q+=" from ";
+        q+=fptr->icfs_map_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=ftn;
+        q+=" from ";
+        q+=fptr->function_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=rtn;
+        q+=" from ";
+        q+=fptr->relocs_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=typ;
+        q+=" from ";
+        q+=fptr->types_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=dtn;
+        q+=" from ";
+        q+=fptr->scoop_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=dtn_part2;
+        q+=" from ";
+        q+=fptr->scoop_table_name+"_part2";
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=ehp;
+        q+=" from ";
+        q+=fptr->ehpgm_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+        q="select * into ";
+        q+=css;
+        q+=" from ";
+        q+=fptr->ehcss_table_name;
+        q+=" ;";
+        dbintr->issueQuery(q);
+
+	// update the variant dependency table to represent the deep clone 
+	q =     "update variant_dependency set file_id='" + 
+		to_string(newfid) + 
+		"' where variant_id='" +
+		to_string(getBaseID()) + 
+		"' AND file_id='" +
+		to_string(fptr->getBaseID()) + 
+		"' ;";
+        dbintr->issueQuery(q);
+
+
+	return newfile;
+
+}
+
+void VariantID_t::WriteToDB()
+{
+	assert(isRegistered());
+
+	std::string q="update variant_info SET ";
+	q+=" schema_version_id = '" + to_string(schema_ver) + "', ";
+	q+=" name = '"  + name  + "', ";
+	q+=" orig_variant_id = '" + to_string(orig_pid) + "', ";
+	q+=" doip_id = '" + to_string(getDoipID()) + "' ";
+	q+=" where variant_id = '" + to_string(getBaseID()) + "';";
+
+	dbintr->issueQuery(q);
+}
+
+std::ostream& IRDB_SDK::operator<<(std::ostream& out, const IRDB_SDK::VariantID_t& pid)
+{
+
+	out << "(" << 
+		"variant_id=" << pid.getBaseID()            << ":" <<
+		"orig_pid="   << pid.getOriginalVariantID() << ":" <<
+		"name="       << pid.getName()              << 
+		")" ;
+	return out;
+}
+
+
+void VariantID_t::DropFromDB()
+{
+	assert(isRegistered());
+
+	string q;
+	q+=string("delete from variant_dependency where variant_id = '") + to_string(getBaseID()) + string("';");
+	q+=string("delete from variant_info where variant_id = '") + to_string(getBaseID()) + string("';");
+
+	dbintr->issueQuery(q);
+
+	setBaseID(NOT_IN_DATABASE);
+	orig_pid=NOT_IN_DATABASE;
+        schema_ver=CURRENT_SCHEMA;
+}
+
+
+IRDB_SDK::File_t* VariantID_t::getMainFile() const
+{
+	for(
+		auto it=files.begin();
+		it!=files.end();
+		++it
+	   )
+	{
+		if ((*it)->getURL().find("a.ncexe") != string::npos)
+			return *it;
+	}
+	/* we should have found the main file somewhere. */
+	assert(0);
+}
+
+
+
+void VariantID_t::ReadFilesFromDB()
+{
+
+	std::string q= "select file_info.orig_file_id, file_info.address_table_name, "
+		" file_info.instruction_table_name, file_info.icfs_table_name,file_info.icfs_map_table_name, "
+		" file_info.function_table_name, file_info.relocs_table_name, file_info.types_table_name, "
+		" file_info.scoop_table_name, file_info.ehpgm_table_name, file_info.ehcss_table_name, file_info.file_id, file_info.url, file_info.hash,"
+		" file_info.arch, file_info.type, file_info.elfoid, file_info.doip_id "
+		" from file_info,variant_dependency "
+		" where variant_dependency.variant_id = '" + to_string(getBaseID()) + "' AND "
+		" file_info.file_id = variant_dependency.file_id ; "; 
+
+	dbintr->issueQuery(q);
+
+	while(!dbintr->isDone())
+	{
+// file_info.file_id, file_info.url, file_info.hash, file_info.arch, file_info.type, file_info.doip_id
+
+		db_id_t file_id=atoi(dbintr->getResultColumn("file_id").c_str());
+		db_id_t orig_fid=atoi(dbintr->getResultColumn("orig_file_id").c_str());
+		std::string url=dbintr->getResultColumn("url");
+		std::string hash=dbintr->getResultColumn("hash");
+		std::string type=dbintr->getResultColumn("type");
+		int oid=atoi(dbintr->getResultColumn("elfoid").c_str());
+		db_id_t doipid=atoi(dbintr->getResultColumn("doip_id").c_str());
+        	std::string atn=(BaseObj_t::dbintr->getResultColumn("address_table_name"));
+        	std::string ftn=(BaseObj_t::dbintr->getResultColumn("function_table_name"));
+        	std::string itn=(BaseObj_t::dbintr->getResultColumn("instruction_table_name"));
+        	std::string dtn=(BaseObj_t::dbintr->getResultColumn("scoop_table_name"));
+        	std::string ehp=(BaseObj_t::dbintr->getResultColumn("ehpgm_table_name"));
+        	std::string css=(BaseObj_t::dbintr->getResultColumn("ehcss_table_name"));
+        	std::string icfs=(BaseObj_t::dbintr->getResultColumn("icfs_table_name"));
+        	std::string icfs_map=(BaseObj_t::dbintr->getResultColumn("icfs_map_table_name"));
+        	std::string rtn=(BaseObj_t::dbintr->getResultColumn("relocs_table_name"));
+        	std::string typ=(BaseObj_t::dbintr->getResultColumn("types_table_name"));
+
+
+		File_t *newfile=new File_t(file_id,orig_fid,url,hash,type,oid,atn,ftn,itn,icfs,icfs_map,rtn,typ,dtn,ehp,css,doipid);
+
+// std::cout<<"Found file "<<file_id<<"."<<std::endl;
+// std::cout<<"  atn: " << atn << " ftn: " << ftn << " rtn: " << rtn << " typ: " << typ << std::endl;
+
+		files.insert(newfile);
+
+		dbintr->moveToNextRow();
+	}
+}
+
+
+namespace IRDB_SDK
+{
+
+unique_ptr<VariantID_t> VariantID_t::factory(const DatabaseID_t& id)
+{
+        return unique_ptr<VariantID_t>(new libIRDB::VariantID_t(id));
+}
+
+unique_ptr<FileIR_t> FileIR_t::factory(VariantID_t *p_progid, File_t* p_fid)
+{
+	const auto progid=dynamic_cast<libIRDB::VariantID_t*>(p_progid);
+	const auto fid=dynamic_cast<libIRDB::File_t*>(p_fid);
+        return unique_ptr<FileIR_t>(new libIRDB::FileIR_t(*progid,fid));
+}
+
+
+}
+
diff --git a/irdb-lib/libIRDB-deep/src/SConscript b/irdb-lib/libIRDB-deep/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..15daf24c7d1de0049565d3abc0aab12761ac50da
--- /dev/null
+++ b/irdb-lib/libIRDB-deep/src/SConscript
@@ -0,0 +1,28 @@
+import os
+
+Import('env')
+myenv=env
+
+
+libname="irdb-deep"
+files=  '''
+	deep.cpp
+	'''
+cpppath=''' 
+	$IRDB_SDK/include/
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-deep/src
+	$SECURITY_TRANSFORMS_HOME/libMEDSannotation/include
+	$SMPSA_HOME/include/
+	'''
+
+#myenv.Append(CCFLAGS=" -Wall -W -Wextra -Wconversion ")
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS = " -std=c++11 ")
+lib=myenv.SharedLibrary(libname, Split(files), LIBS=Split("irdb-core irdb-util irdb-transform stars MEDSannotation"), LIBPATH=Split("$SECURITY_TRANSFORMS_HOME/lib"))
+
+install=env.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libIRDB-deep/src/deep.cpp b/irdb-lib/libIRDB-deep/src/deep.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1ab77bc43feb4763f7a5b09f906af7f3d2b1ebbd
--- /dev/null
+++ b/irdb-lib/libIRDB-deep/src/deep.cpp
@@ -0,0 +1,167 @@
+
+#include <map>
+#include <set>
+#include <memory>
+#include <deep.hpp>
+#include <MEDS_DeadRegAnnotation.hpp>
+#include <MEDS_MemoryRangeAnnotation.hpp>
+#include <MEDS_SafeFuncAnnotation.hpp>
+
+
+using namespace libIRDB;
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+StarsDeepAnalysis_t::StarsDeepAnalysis_t(IRDB_SDK::FileIR_t* firp, const vector<string>& options)
+	: Transform(firp)
+{
+	for(const auto s : options)
+	{
+		if(s=="SetDeepLoopAnalyses=true")
+			stars_analysis_engine.GetSTARSOptions().SetDeepLoopAnalyses(true);
+		else if(s=="SetConstantPropagation=true")
+			stars_analysis_engine.GetSTARSOptions().SetConstantPropagation(true);
+		else
+			throw invalid_argument("Unknown option: "+s);
+	}
+	stars_analysis_engine.do_STARS(getFileIR());
+}
+
+unique_ptr<IRDB_SDK::FunctionSet_t> StarsDeepAnalysis_t::getLeafFunctions()      const 
+{
+	auto ret=unique_ptr<IRDB_SDK::FunctionSet_t>(new IRDB_SDK::FunctionSet_t);
+	auto &ret_map=*ret;
+	auto meds_ap=stars_analysis_engine.getAnnotations();
+
+	for(auto func : getFileIR()->getFunctions())
+	{
+		auto the_range = meds_ap.getFuncAnnotations().equal_range(func->getName());
+	        /* for each annotation for this instruction */
+       		for (auto it = the_range.first; it != the_range.second; ++it)
+		{
+		 	auto p_annotation=dynamic_cast<MEDS_SafeFuncAnnotation*>(it->second);
+			if(p_annotation==nullptr)
+                                continue;
+
+                        /* bad annotation? */
+                        if(!p_annotation->isLeaf())
+                                continue;
+
+                        /* record dead reg set */
+                        ret_map.insert(func);
+		}
+        }
+
+	return ret;
+}
+
+
+unique_ptr<IRDB_SDK::DeadRegisterMap_t> StarsDeepAnalysis_t::getDeadRegisters()      const 
+{
+	auto ret=unique_ptr<IRDB_SDK::DeadRegisterMap_t>(new IRDB_SDK::DeadRegisterMap_t);
+	auto &ret_map=*ret;
+	auto meds_ap=stars_analysis_engine.getAnnotations();
+	for(auto insn : getFileIR()->getInstructions())
+	{
+		auto the_range = meds_ap.getAnnotations().equal_range(insn->getBaseID());
+	        /* for each annotation for this instruction */
+       		 for (auto it = the_range.first; it != the_range.second; ++it)
+		 {
+			 auto p_annotation=dynamic_cast<MEDS_DeadRegAnnotation*>(it->second);
+			if(p_annotation==nullptr)
+                                continue;
+
+                        /* bad annotation? */
+                        if(!p_annotation->isValid())
+                                continue;
+
+                        /* record dead reg set */
+                        ret_map[insn] =  p_annotation->getRegisterSet();
+		 }
+        }
+
+	return ret;
+}
+
+unique_ptr<IRDB_SDK::StaticGlobalStartMap_t> StarsDeepAnalysis_t::getStaticGlobalRanges() const 
+{
+	auto ret=unique_ptr<IRDB_SDK::StaticGlobalStartMap_t>(new IRDB_SDK::StaticGlobalStartMap_t());
+	auto &ret_map=*ret;
+	auto meds_ap=stars_analysis_engine.getAnnotations();
+	for(auto insn : getFileIR()->getInstructions())
+	{
+		auto the_range = meds_ap.getAnnotations().equal_range(insn->getBaseID());
+	        /* for each annotation for this instruction */
+       		 for (auto it = the_range.first; it != the_range.second; ++it)
+		 {
+		 	auto p_annotation=dynamic_cast<MEDS_MemoryRangeAnnotation*>(it->second);
+			if(p_annotation==nullptr)
+                                continue;
+
+                        /* bad annotation? */
+                        if(!p_annotation->isValid())
+                                continue;
+
+			if(!p_annotation->isStaticGlobalRange())
+				continue;
+
+			// record the range minimum. 
+                        ret_map[insn] =  p_annotation->getRangeMin();
+		 }
+        }
+
+	return ret;
+}
+
+unique_ptr<IRDB_SDK::RangeSentinelSet_t> StarsDeepAnalysis_t::getRangeSentinels()      const 
+{
+	auto ret=unique_ptr<IRDB_SDK::RangeSentinelSet_t>(new IRDB_SDK::RangeSentinelSet_t);
+	auto meds_ap=stars_analysis_engine.getAnnotations();
+	for(auto insn : getFileIR()->getInstructions())
+	{
+		auto the_range = meds_ap.getAnnotations().equal_range(insn->getBaseID());
+	        /* for each annotation for this instruction */
+       		 for (auto it = the_range.first; it != the_range.second; ++it)
+		 {
+		 	auto p_annotation=dynamic_cast<MEDS_MemoryRangeAnnotation*>(it->second);
+			if(p_annotation==nullptr)
+                                continue;
+
+                        /* bad annotation? */
+                        if(!p_annotation->isValid())
+                                continue;
+
+			if(!p_annotation->isSentinel())
+				continue;
+
+			/* record sentinal marker. */
+			ret->insert(insn);
+		 }
+        }
+	return ret;
+}
+
+
+unique_ptr<IRDB_SDK::DeepAnalysis_t> IRDB_SDK::DeepAnalysis_t::factory(FileIR_t* firp, const AnalysisEngine_t& ae, const vector<string>& options)
+{
+
+	auto ret=unique_ptr<IRDB_SDK::DeepAnalysis_t>();
+		
+	switch(ae)
+	{
+		case IRDB_SDK::aeSTARS:
+		{
+			ret.reset(new libIRDB::StarsDeepAnalysis_t(firp,options));
+			break;
+		}
+		default:
+		{
+			throw std::invalid_argument("AnalysisEngine_t value not supported");
+		}
+
+	}
+	return ret;
+}
+
+
diff --git a/irdb-lib/libIRDB-deep/src/deep.hpp b/irdb-lib/libIRDB-deep/src/deep.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..6943da676fbd16caf9b0a49d2d806617906eb284
--- /dev/null
+++ b/irdb-lib/libIRDB-deep/src/deep.hpp
@@ -0,0 +1,34 @@
+
+#include <irdb-core>
+#include <irdb-transform>
+#include <irdb-deep>
+#include <memory>
+#include <vector>
+
+#include <stars.h>
+
+
+namespace libIRDB
+{
+	using namespace std;
+
+	class StarsDeepAnalysis_t : public IRDB_SDK::DeepAnalysis_t, protected IRDB_SDK::Transform
+	{
+		private:
+			StarsDeepAnalysis_t()                           = delete;
+			StarsDeepAnalysis_t(const StarsDeepAnalysis_t& copy) = delete;
+
+		public:
+
+			StarsDeepAnalysis_t(IRDB_SDK::FileIR_t* firp, const vector<string>& options={});
+
+			unique_ptr<IRDB_SDK::FunctionSet_t         > getLeafFunctions()      const ;
+			unique_ptr<IRDB_SDK::DeadRegisterMap_t     > getDeadRegisters()      const ;
+			unique_ptr<IRDB_SDK::StaticGlobalStartMap_t> getStaticGlobalRanges() const ;
+			unique_ptr<IRDB_SDK::RangeSentinelSet_t    > getRangeSentinels()     const ;
+
+		private:
+			STARS::IRDB_Interface_t stars_analysis_engine;
+
+	};
+}
diff --git a/irdb-lib/libIRDB-elfdep/SConscript b/irdb-lib/libIRDB-elfdep/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..f0e0b9fd099936cb34955e3edbf6031acbe0dace
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/SConscript
@@ -0,0 +1,7 @@
+import os
+
+Import('env')
+
+lib=SConscript("src/SConscript")
+
+Return('lib')
diff --git a/irdb-lib/libIRDB-elfdep/SConstruct b/irdb-lib/libIRDB-elfdep/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..4d6381b5999d3e6d4e4687fc95f444ea2c4c5747
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/SConstruct
@@ -0,0 +1,8 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return(lib)
diff --git a/irdb-lib/libIRDB-elfdep/src/SConscript b/irdb-lib/libIRDB-elfdep/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..dc8652648f1822c490a9b6f46d906450c9f41dd6
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/src/SConscript
@@ -0,0 +1,29 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+files="elfdep.cpp"
+
+cpppath='''
+	 .
+         $IRDB_SDK/include
+         $SECURITY_TRANSFORMS_HOME/libIRDB/include
+         $SECURITY_TRANSFORMS_HOME/libtransform/include
+        '''
+
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split("irdb-core irdb-transform")
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS = " -std=c++11 ")
+
+lib=myenv.SharedLibrary("irdb-elfdep",  Split(files), LIBPATH=LIBPATH, LIBS=LIBS)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libIRDB-elfdep/src/SConstruct b/irdb-lib/libIRDB-elfdep/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..6c6fd8ea22a97d734ad3e4f3e5a937340c63375d
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/src/SConstruct
@@ -0,0 +1,30 @@
+import os
+import utils
+
+
+env=Environment()
+Export('env')
+
+env.Replace(debug=ARGUMENTS.get("debug",0))
+
+
+if int(env['debug']) == 1:
+        print "Setting debug mode"
+        env.Append(CFLAGS=" -g ")
+        env.Append(CXXFLAGS=" -g ")
+        env.Append(LINKFLAGS=" -g ")
+else:
+        print "Setting release mode"
+        env.Append(CFLAGS=" -O3 ")
+        env.Append(CXXFLAGS=" -O3 ")
+        env.Append(LINKFLAGS=" -O3 ")
+
+lib=SConscript("SConscript")
+
+pedi = Command( target = "./testoutput",
+                source = "./SConscript",
+                action = "cd "+os.environ['SECURITY_TRANSFORMS_HOME']+" ; " + os.environ['PEDI_HOME']+"/pedi -m manifest.txt " )
+
+Depends(pedi,lib);
+Default(pedi)
+
diff --git a/irdb-lib/libIRDB-elfdep/src/elfdep.cpp b/irdb-lib/libIRDB-elfdep/src/elfdep.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..78fa36b08f26ccb4cf8ed9d5c73ffe66bfa53fd5
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/src/elfdep.cpp
@@ -0,0 +1,541 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <irdb-core>
+#include <irdb-transform>
+#include <irdb-elfdep>
+#include <stdlib.h>
+#include <memory>
+#include <math.h>
+#include <elf.h>
+#include <libElfDep.hpp>
+#include <iterator>
+#include <algorithm>
+
+using namespace libIRDB;
+using namespace std;
+
+// use some of IRDB_SDK, without committing to all of it.
+// it's too confusing to use libIRDB namespace as well as the IRDB_SDK namespace;
+using IRDB_SDK::VirtualOffset_t;
+using IRDB_SDK::Relocation_t;
+using IRDB_SDK::Instruction_t;
+using IRDB_SDK::DataScoop_t;
+
+// defines
+#define REV_ALLOF(a) rbegin(a), rend(a)
+#define ALLOF(a) begin(a), end(a)
+
+// static helpers
+
+// use this to determine whether a scoop has a given name.
+static struct ScoopFinder : binary_function<const IRDB_SDK::DataScoop_t*,const string,bool>
+{
+	// declare a simple scoop finder function that finds scoops by name
+	bool operator()(const IRDB_SDK::DataScoop_t* scoop, const string& name) const
+	{
+		return (scoop->getName() == name);
+	};
+} finder;
+
+static IRDB_SDK::DataScoop_t* find_scoop(IRDB_SDK::FileIR_t *firp,const string &name)
+{
+	auto it=find_if(firp->getDataScoops().begin(), firp->getDataScoops().end(), bind2nd(finder, name)) ;
+	if( it != firp->getDataScoops().end() )
+		return *it;
+	return NULL;
+};
+
+static unsigned int add_to_scoop(const string &str, IRDB_SDK::DataScoop_t* scoop) 
+{
+	// assert that this scoop is unpinned.  may need to enable --step move_globals --step-option move_globals:--cfi
+	assert(scoop->getStart()->getVirtualOffset()==0);
+	int len=str.length();
+	scoop->setContents(scoop->getContents()+str);
+	VirtualOffset_t oldend=scoop->getEnd()->getVirtualOffset();
+	VirtualOffset_t newend=oldend+len;
+	scoop->getEnd()->setVirtualOffset(newend);
+	return oldend+1;
+};
+
+template<int ptrsize>
+static void insert_into_scoop_at(const string &str, IRDB_SDK::DataScoop_t* scoop, IRDB_SDK::FileIR_t* firp, const unsigned int at) 
+{
+	// assert that this scoop is unpinned.  may need to enable --step move_globals --step-option move_globals:--cfi
+	assert(scoop->getStart()->getVirtualOffset()==0);
+	int len=str.length();
+	string new_scoop_contents=scoop->getContents();
+	new_scoop_contents.insert(at,str);
+	scoop->setContents(new_scoop_contents);
+
+	VirtualOffset_t oldend=scoop->getEnd()->getVirtualOffset();
+	VirtualOffset_t newend=oldend+len;
+	scoop->getEnd()->setVirtualOffset(newend);
+
+	// update each reloc to point to the new location.
+	for_each(scoop->getRelocations().begin(), scoop->getRelocations().end(), [str,at](IRDB_SDK::Relocation_t* reloc)
+	{
+		if((unsigned int)reloc->getOffset()>=at)
+			reloc->setOffset(reloc->getOffset()+str.size());
+		
+	});
+
+	// check relocations for pointers to this object.
+	// we'll update dataptr_to_scoop relocs, but nothing else
+	// so assert if we find something else
+	for_each(firp->getRelocations().begin(), firp->getRelocations().end(), [scoop](IRDB_SDK::Relocation_t* reloc)
+	{
+		auto wrt=dynamic_cast<IRDB_SDK::DataScoop_t*>(reloc->getWRT());
+		assert(wrt != scoop || reloc->getType()=="dataptr_to_scoop");
+	});
+
+	// for each scoop
+	for_each(firp->getDataScoops().begin(), firp->getDataScoops().end(), [&str,scoop,firp,at](IRDB_SDK::DataScoop_t* scoop_to_update)
+	{
+		// for each relocation for that scoop
+		for_each(scoop_to_update->getRelocations().begin(), scoop_to_update->getRelocations().end(), [&str,scoop,firp,scoop_to_update,at](IRDB_SDK::Relocation_t* reloc)
+		{
+			// if it's a reloc that's wrt scoop
+			auto wrt=dynamic_cast<IRDB_SDK::DataScoop_t*>(reloc->getWRT());
+			if(wrt==scoop)
+			{
+				// then we need to update the scoop
+				if(reloc->getType()=="dataptr_to_scoop")
+				{
+					string contents=scoop_to_update->getContents();
+					// subtract the stringsize from the (implicitly stored) addend
+					// taking pointer size into account.
+					switch(ptrsize)
+					{
+						case 4:
+						{
+							unsigned int val=*((unsigned int*)&contents.c_str()[reloc->getOffset()]); 
+							if(val>=at)
+								val +=str.size();
+							contents.replace(reloc->getOffset(), ptrsize, (const char*)&val, ptrsize);
+							break;
+						
+						}
+						case 8:
+						{
+							unsigned long long val=*((long long*)&contents.c_str()[reloc->getOffset()]); 
+							if(val>=at)
+								val +=str.size();
+							contents.replace(reloc->getOffset(), ptrsize, (const char*)&val, ptrsize);
+							break;
+
+						}
+						default: 
+							assert(0);
+					}
+					scoop_to_update->setContents(contents);
+				}
+			}	
+
+		});
+		
+	});
+};
+
+template<int ptrsize>
+static void prefix_scoop(const string &str, IRDB_SDK::DataScoop_t* scoop, IRDB_SDK::FileIR_t* firp) 
+{
+	insert_into_scoop_at<ptrsize>(str,scoop,firp,0);
+};
+
+
+// Public interfaces for ElfDependencies_t
+
+
+
+// constructors
+ElfDependencies_t::ElfDependencies_t(IRDB_SDK::FileIR_t* firp)
+	: Transform(firp)
+{
+	typedef ElfDependencies_t::ElfDependenciesImpl_t<Elf64_Sym, Elf64_Rela, Elf64_Dyn, R_X86_64_GLOB_DAT, 32, 8> ElfDependencies64_t;
+	typedef ElfDependencies_t::ElfDependenciesImpl_t<Elf32_Sym, Elf32_Rel, Elf32_Dyn, R_386_GLOB_DAT, 8, 4> ElfDependencies32_t;
+
+	if(firp->getArchitectureBitWidth()==32)
+		transformer.reset(new ElfDependencies32_t(firp));
+	else if(firp->getArchitectureBitWidth()==64)
+		transformer.reset(new ElfDependencies64_t(firp));
+	else
+		assert(0);
+}
+
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::ElfDependenciesImpl_t(IRDB_SDK::FileIR_t* firp)
+	: ElfDependencies_t::ElfDependenciesBase_t(firp)
+{
+}
+
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+pair<IRDB_SDK::DataScoop_t*,int> ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::appendGotEntry(const string &name)
+{
+	auto got_scoop=add_got_entry(name);
+	return {got_scoop,0};
+}
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+IRDB_SDK::Instruction_t* ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::appendPltEntry(const string &name)
+{
+
+	static int labelcounter=0;
+
+	stringstream labelstream;
+	labelstream << "L_pltentry_" << labelcounter++;
+
+	auto got_scoop=add_got_entry(name);
+
+	auto newinsn=addNewAssembly(labelstream.str()+": jmp [rel "+labelstream.str()+"]");
+	
+	/*
+	auto newreloc=new Relocation_t(BaseObj_t::NOT_IN_DATABASE, 0, "pcrel", got_scoop);
+
+	dynamic_cast<libIRDB::Instruction_t*>(newinsn)->GetRelocations().insert(newreloc);
+	dynamic_cast<libIRDB::FileIR_t*>(getFileIR())->GetRelocations().insert(newreloc);
+	*/
+	auto newreloc=getFileIR()->addNewRelocation(newinsn, 0,"pcrel", got_scoop);
+	(void)newreloc; // just give to IR.
+	newinsn->getAddress()->setFileID(getFileIR()->getFile()->getBaseID());
+
+	return newinsn;
+}
+
+
+
+
+
+// please  keep this if 0, as we likely want to add plt/got entries in a library later, but
+// we need a use case to test this code -- it was copied from CFI.
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+IRDB_SDK::Instruction_t* ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::find_runtime_resolve(IRDB_SDK::DataScoop_t* gotplt_scoop)
+{
+	const auto firp=getFileIR();
+	// find any data_to_insn_ptr reloc for the gotplt scoop
+	auto it=find_if(gotplt_scoop->getRelocations().begin(), gotplt_scoop->getRelocations().end(), [](IRDB_SDK::Relocation_t* reloc)
+	{
+		return reloc->getType()=="data_to_insn_ptr";
+	});
+	// there _should_ be one.
+	assert(it!=gotplt_scoop->getRelocations().end());
+
+	Relocation_t* reloc=*it;
+	auto wrt=dynamic_cast<Instruction_t*>(reloc->getWRT());
+	assert(wrt);	// should be a WRT
+	assert(wrt->getDisassembly().find("push ") != string::npos);	// should be push K insn
+	return wrt->getFallthrough();	// jump to the jump, or not.. doesn't matter.  zopt will fix
+}
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+IRDB_SDK::DataScoop_t* ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::add_got_entry(const std::string& name)
+{
+	const auto firp=getFileIR(); // dynamic_cast<libIRDB::FileIR_t*>(getFileIR());
+	// find relevant scoops
+	auto dynamic_scoop=find_scoop(firp,".dynamic");
+	// auto gotplt_scoop=find_scoop(firp,".got.plt");
+	//auto got_scoop=find_scoop(firp,".got");
+	auto dynstr_scoop=find_scoop(firp,".dynstr");
+	auto dynsym_scoop=find_scoop(firp,".dynsym");
+	auto relaplt_scoop=find_scoop(firp,".rela.dyn coalesced w/.rela.plt");
+	auto relplt_scoop=find_scoop(firp,".rel.dyn coalesced w/.rel.plt");
+	auto relscoop=relaplt_scoop!=NULL ?  relaplt_scoop : relplt_scoop;
+	auto gnu_version_scoop=find_scoop(firp,".gnu.version");
+
+
+	// if there is versioning info in this binary, assert we unpinned it.
+	if(gnu_version_scoop)
+		assert(gnu_version_scoop->getStart()->getVirtualOffset()==0);
+
+	if (!relscoop) 
+		throw std::logic_error("Cannot find rela.plt or rel.plt. Did you remember to use move_globals with --elf_tables?");
+
+	// add 0-init'd pointer to table
+	auto new_got_entry_str=string(ptrsize,0);	 // zero-init a pointer-sized string
+
+
+	// create a new, unpinned, rw+relro scoop that's an empty pointer.
+	const auto start_addr=firp->addNewAddress(firp->getFile()->getBaseID(), 0);
+	const auto end_addr  =firp->addNewAddress(firp->getFile()->getBaseID(), ptrsize-1);
+	auto external_func_addr_scoop=firp->addNewDataScoop(name,start_addr,end_addr,NULL,6,true,new_got_entry_str);
+
+	// add string to string table 
+	auto dl_str_pos=add_to_scoop(name+'\0', dynstr_scoop);
+
+	// add symbol to dlsym
+	T_Elf_Sym dl_sym;
+	memset(&dl_sym,0,sizeof(T_Elf_Sym));
+	dl_sym.st_name=dl_str_pos;
+	dl_sym.st_info=((STB_GLOBAL<<4)| (STT_OBJECT));
+	string dl_sym_str((const char*)&dl_sym, sizeof(T_Elf_Sym));
+	unsigned int dl_pos=add_to_scoop(dl_sym_str,dynsym_scoop);
+
+	// if there is versioning info in this binary, update it.
+	if(gnu_version_scoop)
+	{
+		// update the gnu.version section so that the new symbol has a version.
+		const auto new_version_str=string("\0\0", 2);	 // \0\0 means *local*, as in, don't index the gnu.verneeded array.
+		add_to_scoop(new_version_str,gnu_version_scoop);
+	}
+
+	
+
+	// find the rela count.  can't insert before that.
+	int rela_count=0;
+	for(int i=0;i+sizeof(T_Elf_Dyn)<dynamic_scoop->getSize(); i+=sizeof(T_Elf_Dyn))
+	{
+		T_Elf_Dyn &dyn_entry=*(T_Elf_Dyn*)&dynamic_scoop->getContents().c_str()[i];
+		if(dyn_entry.d_tag==DT_RELACOUNT)	 // diff than rela size.
+		{
+			// add to the size
+			rela_count=dyn_entry.d_un.d_val;
+			break;
+		}
+	}
+
+	// create the new reloc 
+	T_Elf_Rela dl_rel;
+	memset(&dl_rel,0,sizeof(dl_rel));
+	auto r_info_tmp=(decltype(dl_rel.r_info))dl_pos;
+	dl_rel.r_info= ((r_info_tmp/sizeof(T_Elf_Sym)) <<rela_shift ) | reloc_type;
+
+	string dl_rel_str((const char*)&dl_rel, sizeof(dl_rel));
+
+// need to fixup relocs
+	unsigned int at=rela_count*sizeof(T_Elf_Rela);
+	insert_into_scoop_at<ptrsize>(dl_rel_str, relscoop, firp, at);
+
+	/*
+	auto dl_reloc=new Relocation_t(BaseObj_t::NOT_IN_DATABASE,  at+((uintptr_t)&dl_rel.r_offset -(uintptr_t)&dl_rel), "dataptr_to_scoop", external_func_addr_scoop);
+	dynamic_cast<libIRDB::DataScoop_t*>(relscoop)->GetRelocations().insert(dl_reloc);
+	firp->GetRelocations().insert(dl_reloc);
+	*/
+	auto dl_reloc=firp->addNewRelocation(relscoop,at+((uintptr_t)&dl_rel.r_offset -(uintptr_t)&dl_rel), "dataptr_to_scoop", external_func_addr_scoop);
+	(void)dl_reloc; // just give to IR;
+
+	for(int i=0;i+sizeof(T_Elf_Dyn)<dynamic_scoop->getSize(); i+=sizeof(T_Elf_Dyn))
+	{
+		// cast the index'd c_str to an Elf_Dyn pointer and deref it to assign to a 
+		// reference structure.  That way editing the structure directly edits the string.
+		T_Elf_Dyn &dyn_entry=*(T_Elf_Dyn*)&dynamic_scoop->getContents().c_str()[i];
+		if(dyn_entry.d_tag==DT_RELASZ)
+			// add to the size
+			dyn_entry.d_un.d_val+=sizeof(T_Elf_Rela);
+
+		// we insert the zest_cfi_dispatch symbol after the relative relocs.
+		// but we need to adjust the start if there are no relative relocs.
+		if(at == 0  && dyn_entry.d_tag==DT_RELA)
+			// subtract from the start.
+			dyn_entry.d_un.d_val-=sizeof(T_Elf_Rela);
+
+	}
+	return external_func_addr_scoop;
+}
+
+#if 0
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+bool ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::add_got_entries()
+{
+	const auto firp=getFileIR();
+
+	// find all the necessary scoops;
+	auto dynamic_scoop=find_scoop(firp,".dynamic");
+	auto gotplt_scoop=find_scoop(firp,".got.plt");
+	auto got_scoop=find_scoop(firp,".got");
+	auto dynstr_scoop=find_scoop(firp,".dynstr");
+	auto dynsym_scoop=find_scoop(firp,".dynsym");
+	auto relaplt_scoop=find_scoop(firp,".rela.dyn coalesced w/.rela.plt");
+	auto relplt_scoop=find_scoop(firp,".rel.dyn coalesced w/.rel.plt");
+	auto relscoop=relaplt_scoop!=NULL ?  relaplt_scoop : relplt_scoop;
+
+	// Instruction_t* to_dl_runtime_resolve=find_runtime_resolve<T_Elf_Sym,T_Elf_Rela, T_Elf_Dyn, rela_shift, reloc_type, ptrsize>(gotplt_scoop);
+	Instruction_t* to_dl_runtime_resolve=find_runtime_resolve(gotplt_scoop);
+
+
+	// add necessary GOT entries.
+	// add_got_entry<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>("zest_cfi_dispatch");
+	add_got_entry("zest_cfi_dispatch");
+
+
+	// also add a zest cfi "function" that's exported so dlsym can find it.
+	auto zestcfi_str_pos=add_to_scoop(string("zestcfi")+'\0', dynstr_scoop);
+
+	// add zestcfi symbol to binary
+	T_Elf_Sym zestcfi_sym;
+	memset(&zestcfi_sym,0,sizeof(T_Elf_Sym));
+	zestcfi_sym.st_name=zestcfi_str_pos;
+	zestcfi_sym.st_size=1234;
+	zestcfi_sym.st_info=((STB_GLOBAL<<4)| (STT_FUNC));
+	string zestcfi_sym_str((const char*)&zestcfi_sym, sizeof(T_Elf_Sym));
+	unsigned int zestcfi_pos=add_to_scoop(zestcfi_sym_str,dynsym_scoop);
+
+	// add "function" for zestcfi"
+	// for now, return that the target is allowed.  the nonce plugin will have to have a slow path for this later.
+	assert(firp->GetArchitectureBitWidth()==64); // fixme for 32-bit, should jmp to ecx.
+	auto zestcfi_function_entry=addNewAssembly(firp,NULL,"jmp r11");
+
+	// this jump can target any IBT in the module.
+	ICFS_t *newicfs=new ICFS_t;
+	for_each(firp->GetInstructions().begin(), firp->GetInstructions().end(), [&](Instruction_t* insn)
+	{
+		if(insn->GetIndirectBranchTargetAddress() != NULL )
+			newicfs->insert(insn);
+	});
+	zestcfi_function_entry->SetIBTargets(newicfs);
+	firp->GetAllICFS().insert(newicfs);
+	firp->AssembleRegistry();
+	
+
+	// add a relocation so that the zest_cfi "function"  gets pointed to by the symbol
+	Relocation_t* zestcfi_reloc=new Relocation_t(BaseObj_t::NOT_IN_DATABASE,  zestcfi_pos+((uintptr_t)&zestcfi_sym.st_value - (uintptr_t)&zestcfi_sym), "data_to_insn_ptr", zestcfi_function_entry);
+	dynsym_scoop->GetRelocations().insert(zestcfi_reloc);
+	firp->GetRelocations().insert(zestcfi_reloc);
+
+
+	// update strtabsz after got/etc entries are added.
+	for(int i=0;i+sizeof(T_Elf_Dyn)<dynamic_scoop->GetSize(); i+=sizeof(T_Elf_Dyn))
+	{
+		T_Elf_Dyn &dyn_entry=*(T_Elf_Dyn*)&dynamic_scoop->GetContents().c_str()[i];
+		if(dyn_entry.d_tag==DT_STRSZ)
+		{
+			dyn_entry.d_un.d_val=dynstr_scoop->GetContents().size();
+		}
+	}
+
+
+	return true;
+}
+#endif
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+void ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::appendLibraryDepedencies(const string &libraryName)
+{
+	const auto firp=getFileIR(); // dynamic_cast<FileIR_t*>(getFileIR());
+
+	auto dynamic_scoop=find_scoop(firp,".dynamic");
+	auto dynstr_scoop=find_scoop(firp,".dynstr");
+
+	// not dynamic executable w/o a .dynamic section.
+	if(!dynamic_scoop)
+		throw std::logic_error("Cannot change libraries in statically linked program");
+
+	// may need to enable --step move_globals --step-option move_globals:--cfi
+	if(dynamic_scoop->getStart()->getVirtualOffset()!=0)
+	{
+		cerr<<"Cannot find relocation-scoop pair:  Did you enable '--step move_globals --step-option move_globals:--cfi' ? "<<endl;
+		exit(1);
+	}
+
+	const auto libld_str_pos=add_to_scoop(libraryName+'\0', dynstr_scoop);
+
+	// a new dt_needed entry for libdl.so
+	auto new_dynamic_entry=T_Elf_Dyn ({});
+	new_dynamic_entry.d_tag=DT_NEEDED;
+	new_dynamic_entry.d_un.d_val=libld_str_pos;
+	const auto new_dynamic_entry_str=string((const char*)&new_dynamic_entry, sizeof(T_Elf_Dyn));
+
+	// a null terminator
+	const auto null_dynamic_entry=T_Elf_Dyn ({});
+	const auto null_dynamic_entry_str=string((const char*)&null_dynamic_entry, sizeof(T_Elf_Dyn));
+
+	// declare an entry for the .dynamic section and add it.
+	auto index=0;
+	while(1)
+	{
+		// assert we don't run off the end.
+		assert((index+1)*sizeof(T_Elf_Dyn) <= dynamic_scoop->getContents().size());
+
+		const auto dyn_ptr=(T_Elf_Dyn*) & dynamic_scoop->getContents().c_str()[index*sizeof(T_Elf_Dyn)];
+	
+		if(memcmp(dyn_ptr,&null_dynamic_entry,sizeof(T_Elf_Dyn)) == 0 )
+		{
+			cout<<"Inserting new DT_NEEDED at index "<<dec<<index<<endl;
+			// found a null terminator entry.
+			for(auto i=0U; i<sizeof(T_Elf_Dyn); i++)
+			{
+				// copy new_dynamic_entry ontop of null entry.
+				auto str=dynamic_scoop->getContents();
+				str[index*sizeof(T_Elf_Dyn) + i ] = ((char*)&new_dynamic_entry)[i];
+				dynamic_scoop->setContents(str);
+			}
+
+			// check if there's room for the new null entry
+			if((index+2)*sizeof(T_Elf_Dyn) <= dynamic_scoop->getContents().size())
+			{
+				/* yes */
+				const auto next_entry=(T_Elf_Dyn*)&dynamic_scoop->getContents().c_str()[(index+1)*sizeof(T_Elf_Dyn)];
+				// assert it's actually null 
+				assert(memcmp(next_entry,&null_dynamic_entry,sizeof(T_Elf_Dyn)) == 0 );
+			}
+			else
+			{
+				// add to the scoop 
+				add_to_scoop(null_dynamic_entry_str,dynamic_scoop);
+			}
+			break;
+		}
+
+		index++;
+	}
+
+	return;
+
+}
+
+template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+void ElfDependencies_t::ElfDependenciesImpl_t<T_Elf_Sym,T_Elf_Rela,T_Elf_Dyn,reloc_type,rela_shift,ptrsize>::prependLibraryDepedencies(const string &libraryName)
+{
+	const auto firp=getFileIR();
+
+	auto dynamic_scoop=find_scoop(firp,".dynamic");
+	auto dynstr_scoop=find_scoop(firp,".dynstr");
+
+	// not dynamic executable w/o a .dynamic section.
+	if(!dynamic_scoop || !dynstr_scoop)
+		throw std::logic_error("Cannot change libraries in statically linked program");
+
+	// may need to enable --step move_globals --step-option move_globals:--cfi
+	if(dynamic_scoop->getStart()->getVirtualOffset()!=0)
+	{
+		cerr<<"Cannot find relocation-scoop pair:  Did you enable '--step move_globals --step-option move_globals:--cfi' ? "<<endl;
+		exit(1);
+	}
+
+	const auto libld_str_pos=add_to_scoop(libraryName+'\0', dynstr_scoop);
+
+	// a new dt_needed entry for libdl.so
+	auto new_dynamic_entry=T_Elf_Dyn ({});
+	new_dynamic_entry.d_tag=DT_NEEDED;
+	new_dynamic_entry.d_un.d_val=libld_str_pos;
+	const auto new_dynamic_entry_str=string((const char*)&new_dynamic_entry, sizeof(T_Elf_Dyn));
+
+	prefix_scoop<ptrsize>(new_dynamic_entry_str,  dynamic_scoop, firp) ;
+}
+
+unique_ptr<IRDB_SDK::ElfDependencies_t> IRDB_SDK::ElfDependencies_t::factory(IRDB_SDK::FileIR_t* firp)
+{
+	return unique_ptr<IRDB_SDK::ElfDependencies_t>(new libIRDB::ElfDependencies_t(firp));
+}
+
diff --git a/irdb-lib/libIRDB-elfdep/src/libElfDep.hpp b/irdb-lib/libIRDB-elfdep/src/libElfDep.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..4b7eb1e5f7818fdb05b0315e05afc202530ab140
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/src/libElfDep.hpp
@@ -0,0 +1,67 @@
+
+#include <irdb-core>
+#include <irdb-transform>
+#include <irdb-elfdep>
+#include <string>
+#include <memory>
+
+
+namespace libIRDB
+{
+
+using namespace std;
+
+class ElfDependencies_t : public IRDB_SDK::Transform, public IRDB_SDK::ElfDependencies_t
+{
+	public:
+
+		ElfDependencies_t(IRDB_SDK::FileIR_t* firp);
+		void prependLibraryDepedencies(const string& libName) { transformer->prependLibraryDepedencies(libName); }
+		void appendLibraryDepedencies(const string& libName)  { transformer->appendLibraryDepedencies(libName); }
+
+		// return scoop and offset
+		pair<IRDB_SDK::DataScoop_t*,int> appendGotEntry(const string &symbolName)  { return transformer->appendGotEntry(symbolName); }
+
+		// return instruction that's the plt entry.
+		IRDB_SDK::Instruction_t* appendPltEntry(const string &symbolName)  { return transformer->appendPltEntry(symbolName); }
+
+	private:
+
+	class ElfDependenciesBase_t : public Transform
+	{
+		public:
+			ElfDependenciesBase_t(IRDB_SDK::FileIR_t* firp) : Transform(firp) {}
+			virtual void prependLibraryDepedencies(const string &libraryName)=0;
+			virtual void appendLibraryDepedencies(const string &libraryName)=0;
+			virtual pair<IRDB_SDK::DataScoop_t*,int> appendGotEntry(const string &name)=0; 
+			virtual IRDB_SDK::Instruction_t* appendPltEntry(const string &name)=0; 
+
+	};
+
+	template<typename T_Elf_Sym, typename T_Elf_Rela, typename T_Elf_Dyn, int reloc_type, int rela_shift, int ptrsize>
+	class ElfDependenciesImpl_t : public ElfDependenciesBase_t
+	{
+
+		public:
+			ElfDependenciesImpl_t(IRDB_SDK::FileIR_t* fipr);
+
+			virtual void prependLibraryDepedencies(const string& libraryName);
+			virtual void appendLibraryDepedencies(const string& libraryName);
+			virtual pair<IRDB_SDK::DataScoop_t*,int> appendGotEntry(const string& name); 
+			virtual IRDB_SDK::Instruction_t* appendPltEntry(const string& name); 
+			
+
+		private:
+			bool add_dl_support();
+			IRDB_SDK::Instruction_t* find_runtime_resolve(IRDB_SDK::DataScoop_t* gotplt_scoop);
+			IRDB_SDK::DataScoop_t* add_got_entry(const std::string& name);
+			bool add_libdl_as_needed_support(string libName);
+			bool execute();
+
+	};
+
+	unique_ptr<ElfDependenciesBase_t> transformer;
+};
+
+
+}
diff --git a/irdb-lib/libIRDB-elfdep/test/.gitignore b/irdb-lib/libIRDB-elfdep/test/.gitignore
new file mode 100644
index 0000000000000000000000000000000000000000..6855a42d7a3b1ed434cd9b9a8b83ee5b74e3a04f
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/.gitignore
@@ -0,0 +1,9 @@
+edt.exe
+edt.o
+edt.out
+edt_driver.o
+elf_dep_test.os
+libelf_dep_test.so
+peasoup_executable_directory.*
+tmp.out
+
diff --git a/irdb-lib/libIRDB-elfdep/test/SConscript b/irdb-lib/libIRDB-elfdep/test/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..3f62a1b032e5b3d6ac70e2ea1f60adb7cbba3d7d
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/SConscript
@@ -0,0 +1,36 @@
+import os
+
+
+
+Import('env')
+
+# import and create a copy of the environment so we don't screw up anyone elses env.
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+myenv.Replace(ZIPR_HOME=os.environ['ZIPR_HOME'])
+myenv.Replace(ZIPR_SDK=os.environ['ZIPR_SDK'])
+myenv.Replace(IRDB_SDK=os.environ['IRDB_SDK'])
+myenv.Replace(ZIPR_INSTALL=os.environ['ZIPR_INSTALL'])
+
+myenv.Replace(CXXFLAGS = " -g -std=c++11 -Wall ")
+myenv.Append(LINKFLAGS = " -Wl,-unresolved-symbols=ignore-in-shared-libs ")
+
+cpppath=''' 
+	 $IRDB_SDK/include 
+	'''
+
+
+files=Glob( Dir('.').srcnode().abspath+"/edt*.cpp")
+
+pgm="edt.exe"
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split("irdb-core irdb-transform irdb-elfdep")
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+pgm=myenv.Program(pgm,  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install/", pgm)
+Default(install)
+
+files=Glob( Dir('.').srcnode().abspath+"/elf_dep_test*.cpp")
+sharedLib=myenv.SharedLibrary("elf_dep_test",  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+Default(sharedLib)
diff --git a/irdb-lib/libIRDB-elfdep/test/SConstruct b/irdb-lib/libIRDB-elfdep/test/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..7fe41a3bcc605387c2eaafceaa7e944ab0d252fb
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/SConstruct
@@ -0,0 +1,15 @@
+import os
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+
+pedi = Command( target = "./testoutput",
+                source = "./SConscript",
+                action = "cd "+os.environ['SECURITY_TRANSFORMS_HOME']+" ; " + os.environ['PEDI_HOME']+"/pedi -m manifest.txt ; cd - " )
+
+Depends(pedi,lib);
+Default(pedi)
+
diff --git a/irdb-lib/libIRDB-elfdep/test/edt.cpp b/irdb-lib/libIRDB-elfdep/test/edt.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ff1d95391fe8128bf79fa90e1c5d9eba4875a977
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/edt.cpp
@@ -0,0 +1,68 @@
+
+#include "edt.hpp"
+#include <irdb-elfdep>
+#include <algorithm> 
+
+using namespace IRDB_SDK;
+using namespace std;
+using namespace ElfDep_Tester;
+
+
+ElfDep_Tester_t::ElfDep_Tester_t(FileIR_t* firp)
+	: Transform (firp)
+{
+}
+
+
+#define ALLOF(a) begin(a),end(a)
+
+	
+int ElfDep_Tester_t::execute()
+{
+	// insert the PLT and GOT entries needed
+	auto ed=ElfDependencies_t::factory(getFileIR());
+	(void)ed->appendLibraryDepedencies("libelf_dep_test.so");
+	auto edpcb=ed->appendPltEntry("elf_dep_test_callback");
+	auto edvar=ed->appendGotEntry("elf_dep_test_var");
+	auto edvar_scoop=edvar.first;
+	auto edvar_offset=edvar.second;
+
+
+	// find the insertion point.
+	const auto &all_funcs=getFileIR()->getFunctions();
+	const auto main_func_it=find_if(ALLOF(all_funcs), [&](const Function_t* f) { return f->getName()=="main";});
+	assert(main_func_it!=all_funcs.end());		
+	const auto main_func=*main_func_it;
+	auto insert_loc=main_func->getEntryPoint();
+
+
+	// insert the instrumentation
+	auto tmp=insert_loc;
+    	(void)insertAssemblyBefore(tmp," push rdi") ;
+	tmp=  insertAssemblyAfter(tmp," push rsi ") ;
+	tmp=  insertAssemblyAfter(tmp," push rdx") ;
+	tmp=  insertAssemblyAfter(tmp," push rcx ") ;
+	tmp=  insertAssemblyAfter(tmp," push r8 ") ;
+	tmp=  insertAssemblyAfter(tmp," push r9 ") ;
+	tmp=  insertAssemblyAfter(tmp," call 0 ", edpcb) ;
+	tmp=  insertAssemblyAfter(tmp," L1: mov rcx, [rel L1]");
+	auto got_insn=tmp;
+	tmp=  insertAssemblyAfter(tmp," inc dword [rcx]");
+	tmp=  insertAssemblyAfter(tmp," call 0", edpcb);
+	tmp=  insertAssemblyAfter(tmp," pop r9");
+	tmp=  insertAssemblyAfter(tmp," pop r8");
+	tmp=  insertAssemblyAfter(tmp," pop rcx");
+	tmp=  insertAssemblyAfter(tmp," pop rdx");
+	tmp=  insertAssemblyAfter(tmp," pop rsi");
+	tmp=  insertAssemblyAfter(tmp," pop rdi");
+
+
+	// map the load to point at the GOT entry.
+	auto got_reloc=getFileIR()->addNewRelocation(got_insn, edvar_offset, "pcrel", edvar_scoop);
+	(void)got_reloc; // just give to IR
+
+	return 0;
+}
+	
+
+
diff --git a/irdb-lib/libIRDB-elfdep/test/edt.hpp b/irdb-lib/libIRDB-elfdep/test/edt.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..24c082c478f7391dd985b011fcbcfd978cde67c2
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/edt.hpp
@@ -0,0 +1,26 @@
+
+#include <string>
+#include <set>
+#include <irdb-core>
+#include <irdb-transform>
+
+namespace ElfDep_Tester
+{
+
+using namespace IRDB_SDK;
+using namespace std;
+
+
+typedef set<string> StringSet_t;
+class ElfDep_Tester_t : Transform
+{
+	public:
+	ElfDep_Tester_t(FileIR_t* firp);
+	
+	int execute(); 
+
+	private:
+	
+};
+
+}
diff --git a/irdb-lib/libIRDB-elfdep/test/edt_driver.cpp b/irdb-lib/libIRDB-elfdep/test/edt_driver.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..52d836f477b87b1e49f367205ec58a6450c7c251
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/edt_driver.cpp
@@ -0,0 +1,133 @@
+#include <stdlib.h>
+#include <fstream>
+#include <string>
+#include "edt.hpp"
+#include <irdb-core>
+#include <getopt.h>
+
+using namespace std;
+using namespace IRDB_SDK;
+using namespace ElfDep_Tester;
+
+void usage(string programName)
+{
+	cerr << "Usage: " << programName << " <variant id> " 	<<endl;
+	cout<<"--help,--usage,-?,-h		Display this message"<<endl;
+}
+
+int main(int argc, char **argv)
+{	
+	string programName(argv[0]);
+	char *strtolError = NULL;
+	int transformExitCode = 0;
+	int variantID = -1; 
+	auto pqxx_interface=pqxxDB_t::factory();
+	int exit_code=0;
+
+	/*
+	 * Check that we've been called correctly:
+	 * <program> <variant id> <annotation file>
+	 */
+	if(argc < 2)
+	{
+		usage(programName);
+		exit(1);
+	}
+	variantID = strtol(argv[1], &strtolError, 10);
+	if (*strtolError != '\0')
+	{
+		cerr << "Invalid variantID: " << argv[1] << endl;
+		exit(1);
+	}
+
+	// Parse some options for the transform
+	const static struct option long_options[] = {
+		{"help", no_argument, 0, 'h'},
+		{"usage", no_argument, 0, '?'},
+		{0,0,0,0}
+	};
+	auto short_opts="h?";
+
+	while(1) {
+		int index = 0;
+		int c = getopt_long(argc, argv,short_opts, long_options, &index);
+		if(c == -1)
+			break;
+		switch(c) {
+			case 0:
+				break;
+			case '?':
+			case 'h':
+				usage(argv[0]);
+				exit(1);
+				break;
+			default:
+				break;
+		}
+	}
+
+
+	/* setup the interface to the sql server */
+	BaseObj_t::setInterface(pqxx_interface.get());
+
+	auto pidp=VariantID_t::factory(variantID);
+	assert(pidp && pidp->isRegistered()==true);
+
+	for(set<File_t*>::iterator it=pidp->getFiles().begin();
+	    it!=pidp->getFiles().end();
+		++it)
+	{
+		try 
+		{
+			/* read the IR from the DB */
+			File_t* this_file = *it;
+			auto firp = FileIR_t::factory(pidp.get(), this_file);
+			cout<<"Transforming "<<this_file->getURL()<<endl;
+			assert(firp && pidp);
+
+
+			/*
+			 * Create a transformation and then
+			 * invoke its execution.
+			 */
+				auto ed=ElfDep_Tester_t(firp.get());
+				transformExitCode = ed.execute();
+			/*
+			 * If everything about the transformation
+			 * went okay, then we will write the updated
+			 * set of instructions to the database.
+			 */
+			if (transformExitCode == 0)
+			{
+				if(getenv("MG_NOUPDATE")==NULL)
+				{
+					firp->writeToDB();
+				}
+			}
+			else
+			{
+				cerr << programName << ": transform failed. Check logs." << endl;
+				exit_code=2;
+			}
+		}
+		catch (DatabaseError_t pnide)
+		{
+			cerr << programName << ": Unexpected database error: " << pnide << endl;
+			exit(1);
+		}
+		catch (const std::exception &exc)
+		{
+		    // catch anything thrown within try block that derives from std::exception
+			std::cerr << "Unexpected exception: " << exc.what();
+			exit(1);
+		}
+		catch (...)
+		{
+			cerr << programName << ": Unexpected error" << endl;
+			exit(1);
+		}
+	}
+	pqxx_interface->commit();
+
+	return exit_code;
+}
diff --git a/irdb-lib/libIRDB-elfdep/test/elf_dep_test.cpp b/irdb-lib/libIRDB-elfdep/test/elf_dep_test.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..5f77c041e5159998302399f3bd257bc6163e4675
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/elf_dep_test.cpp
@@ -0,0 +1,13 @@
+
+#include <stdio.h>
+extern "C"
+{
+
+int elf_dep_test_var=0;
+
+void elf_dep_test_callback()
+{
+	printf("Elf_dep_test var = %d\n", elf_dep_test_var);
+}
+
+}
diff --git a/irdb-lib/libIRDB-elfdep/test/test-elfdep.sh b/irdb-lib/libIRDB-elfdep/test/test-elfdep.sh
new file mode 100755
index 0000000000000000000000000000000000000000..39ac850f75d329f0223c1f2e177835917710a161
--- /dev/null
+++ b/irdb-lib/libIRDB-elfdep/test/test-elfdep.sh
@@ -0,0 +1,44 @@
+#!/bin/bash
+
+TMP_ORIG=/tmp/testelfdep.ls.orig.$$
+TMP_ORIG2=/tmp/testelfdep.ls.orig.2.$$
+TMP_ELFDEP=/tmp/testelfdep.ls.elfdep.$$
+
+cleanup_files()
+{
+	rm /tmp/testelfdep.ls* >/dev/null 2>&1
+}
+
+cleanup()
+{
+	echo "************"
+	echo "test failed."
+	echo "************"
+
+	cleanup_files
+	exit 1
+}
+
+	
+# make sure xforms are built
+scons || cleanup
+
+$PSZ /bin/ls ./xxx -c move_globals=on -o move_globals:--elftables -c edt=on || cleanup
+ 
+/bin/ls /tmp > $TMP_ORIG || cleanup
+
+./xxx /tmp > $TMP_ELFDEP || cleanup
+
+echo "Verify external vars was overwritten"
+grep "var = 0" $TMP_ELFDEP || cleanup
+grep "var = 1" $TMP_ELFDEP || cleanup
+
+echo "Verify same output"
+grep -v "var =" $TMP_ELFDEP > $TMP_ORIG2
+diff $TMP_ORIG2 $TMP_ELFDEP
+
+cleanup_files
+
+echo
+echo "test passed."
+echo
diff --git a/irdb-lib/libIRDB-syscall/include/libIRDB-syscall.hpp b/irdb-lib/libIRDB-syscall/include/libIRDB-syscall.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..3ac7c4ccc9e94ae0436d7d16567bd9650a6dd135
--- /dev/null
+++ b/irdb-lib/libIRDB-syscall/include/libIRDB-syscall.hpp
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef libIRDB_syscall
+#define libIRDB_syscall
+
+
+/* Building a CFG depends on core functionality */
+
+#include <vector>
+#include <set>
+#include <map>
+#include <ostream>
+
+
+#include <syscall.hpp>
+
+
+#endif
diff --git a/irdb-lib/libIRDB-syscall/include/syscall.hpp b/irdb-lib/libIRDB-syscall/include/syscall.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..0e54e9931b42fa48e15d4ac3e7f369a844861bde
--- /dev/null
+++ b/irdb-lib/libIRDB-syscall/include/syscall.hpp
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef irdb_syscall_hpp
+#define irdb_syscall_hpp
+
+namespace libIRDB
+{
+
+	class  SyscallSite_t : public IRDB_SDK::SyscallSite_t
+	{
+		public:
+			SyscallSite_t(IRDB_SDK::Instruction_t* p_site, IRDB_SDK::SyscallNumber_t p_num) : site(p_site), num(p_num) {}
+
+			IRDB_SDK::Instruction_t*  getSyscallSite()   const { return site; }
+			IRDB_SDK::Instruction_t*  getSite()          const { return site; }
+			IRDB_SDK::SyscallNumber_t getSyscallNumber() const { return num; }
+
+		private:
+			IRDB_SDK::Instruction_t* site;
+			IRDB_SDK::SyscallNumber_t num;
+	};
+
+	class Syscalls_t : public IRDB_SDK::Syscalls_t
+	{
+		public:
+			Syscalls_t(IRDB_SDK::FileIR_t *the_firp=NULL) { if(the_firp) FindSystemCalls(the_firp); }
+			virtual ~Syscalls_t();
+
+
+
+			const IRDB_SDK::SyscallSiteSet_t& getSyscalls() {return syscalls;}
+		protected:
+			IRDB_SDK::SyscallNumber_t FindSystemCallNumber(IRDB_SDK::Instruction_t* insn, 
+				const IRDB_SDK::InstructionPredecessors_t& preds);
+
+			bool FindSystemCalls(const IRDB_SDK::FileIR_t* firp);
+		private:
+			IRDB_SDK::SyscallSiteSet_t syscalls;
+	};
+
+}
+#endif
+
diff --git a/irdb-lib/libIRDB-syscall/src/SConscript b/irdb-lib/libIRDB-syscall/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..b1d91ed7655ef3401ee373c067c1d06a7fefa917
--- /dev/null
+++ b/irdb-lib/libIRDB-syscall/src/SConscript
@@ -0,0 +1,30 @@
+import os
+
+Import('env')
+myenv=env
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+libname="irdb-syscall"
+files=  '''
+	syscall.cpp
+	'''
+cpppath=''' 
+	$IRDB_SDK/include/
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-core/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-syscall/include/
+	'''
+
+#myenv.Append(CCFLAGS=" -Wall -W -Wextra -Wconversion ")
+
+myenv.Append(CXXFLAGS = " -std=c++11 ")
+
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+lib=myenv.SharedLibrary(libname, Split(files), LIBS=Split("irdb-core irdb-util"), LIBPATH=Split("$SECURITY_TRANSFORMS_HOME/lib"))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libIRDB-syscall/src/SConstruct b/irdb-lib/libIRDB-syscall/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..17f632b8c29cd420163897b1eb044ca3486df362
--- /dev/null
+++ b/irdb-lib/libIRDB-syscall/src/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+install=SConscript("SConscript")
+Return('install')
diff --git a/irdb-lib/libIRDB-syscall/src/syscall.cpp b/irdb-lib/libIRDB-syscall/src/syscall.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..c4fc4e7108c22397f686c72e3819bdaec5b8488e
--- /dev/null
+++ b/irdb-lib/libIRDB-syscall/src/syscall.cpp
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <irdb-core>
+#include <irdb-util>
+#include <irdb-syscall>
+#include <libIRDB-syscall.hpp>
+#include <stdlib.h>
+
+using namespace std;
+using namespace libIRDB;
+
+Syscalls_t::~Syscalls_t()
+{
+	for(auto site : syscalls)
+		delete site;
+	syscalls.clear();
+}
+
+IRDB_SDK::SyscallNumber_t Syscalls_t::FindSystemCallNumber(IRDB_SDK::Instruction_t* insn, const IRDB_SDK::InstructionPredecessors_t& preds)
+{
+	IRDB_SDK::Instruction_t *pred_insn=nullptr;
+
+	for( auto cs_preds=&preds[insn];
+		cs_preds->size()==1;
+		cs_preds=&preds[pred_insn]
+	   )
+	{
+		pred_insn=*(cs_preds->begin());
+
+		string disass=pred_insn->getDisassembly();
+
+		/* look for eax being used or set */
+		if(disass.find("eax")!=string::npos)
+		{
+			string to_find="mov eax,";
+			size_t loc=disass.find(to_find);
+			// check to see if it's a mov of eax
+			if(loc ==string::npos)
+			{
+				// no, quit looking backwards 
+				return IRDB_SDK::sntUnknown;
+			}
+			size_t val=strtol(disass.substr(loc+to_find.length()).c_str(),nullptr,16);
+			// check to see if it's a mov of eax
+
+			return (IRDB_SDK::SyscallNumber_t)val;
+		}
+	}
+
+	return IRDB_SDK::sntUnknown;
+
+}
+
+bool Syscalls_t::FindSystemCalls(const IRDB_SDK::FileIR_t *firp2)
+{
+	auto firp=const_cast<IRDB_SDK::FileIR_t*>(firp2); // discard const qualifer, but we aren't changing anything.
+	assert(firp);
+	auto predsp=IRDB_SDK::InstructionPredecessors_t::factory(firp);
+	auto &preds = * predsp;
+
+	bool found_one=false;
+	for(auto insn : firp->getInstructions())
+	{
+		if(insn->getDisassembly()=="int 0x80") 
+		{
+			auto num=FindSystemCallNumber(insn, preds);
+			syscalls.insert(new libIRDB::SyscallSite_t(insn,num));
+			found_one=true;
+
+			if(getenv("PRINTSYSCALLSFOUND"))
+				cout<<"Found system call "<< insn->getBaseID()<< ":'"<< insn->getDisassembly() << "' with eax value "<< (size_t)num<<endl;
+		}
+	}
+	return found_one;
+
+}
+
+
+
diff --git a/irdb-lib/libIRDB-transform/Makefile b/irdb-lib/libIRDB-transform/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..8eeb9bea022e83cddb938e52c3155e2962f19924
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/Makefile
@@ -0,0 +1,5 @@
+all:
+	cd src; make
+
+clean:
+	cd src; make clean
diff --git a/irdb-lib/libIRDB-transform/SConscript b/irdb-lib/libIRDB-transform/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..f0e0b9fd099936cb34955e3edbf6031acbe0dace
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/SConscript
@@ -0,0 +1,7 @@
+import os
+
+Import('env')
+
+lib=SConscript("src/SConscript")
+
+Return('lib')
diff --git a/irdb-lib/libIRDB-transform/SConstruct b/irdb-lib/libIRDB-transform/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..4d6381b5999d3e6d4e4687fc95f444ea2c4c5747
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/SConstruct
@@ -0,0 +1,8 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return(lib)
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/Makefile.in b/irdb-lib/libIRDB-transform/include-unused-delete-later/Makefile.in
new file mode 100644
index 0000000000000000000000000000000000000000..56fe02141bd2113326a9d6b1af59e3e87a7ace1b
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/Makefile.in
@@ -0,0 +1,18 @@
+
+CXX=@CXX@
+
+LIB=../lib/libtransform.a
+
+OBJS=Rewrite_Utility.o transform.o integertransform.o leapattern.o integertransform64.o integertransform32.o pointercheck64.o
+
+all: $(OBJS)
+
+$(OBJS): ../include/*.hpp 
+
+clean:
+	rm -f $(OBJS)
+
+.cpp.o:
+	$(CXX) -g -c -I. -I../include -I../../libIRDB/include -I../../libMEDSannotation/include -I../../beaengine/include $<
+	ar rc $(LIB) $@
+	cp $(LIB) ../../lib/
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/Rewrite_Utility.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/Rewrite_Utility.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..7a9f1f90a0f1f02a3d981954ec78fdda87a4e81e
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/Rewrite_Utility.hpp
@@ -0,0 +1,58 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <irdb-core>
+
+
+namespace IRDBUtility {
+using namespace IRDB_SDK;
+using namespace std;
+
+//The "first" instruction will have its contents replaced and a duplicate of "first" will be in the follow of first. 
+//This duplicate is returned since the user already has a pointer to first. 
+Instruction_t* insertAssemblyBefore(FileIR_t* virp, Instruction_t* first, string assembly, Instruction_t *target);
+Instruction_t* insertAssemblyBefore(FileIR_t* virp, Instruction_t* first, string assembly);
+Instruction_t* insertDataBitsBefore(FileIR_t* virp, Instruction_t* first, string dataBits, Instruction_t *target);
+Instruction_t* insertDataBitsBefore(FileIR_t* virp, Instruction_t* first, string dataBits);
+
+// insert new instructions after, diff types.
+Instruction_t* insertAssemblyAfter(FileIR_t* virp, Instruction_t* first, string assembly, Instruction_t *target);
+Instruction_t* insertAssemblyAfter(FileIR_t* virp, Instruction_t* first, string assembly);
+Instruction_t* insertDataBitsAfter(FileIR_t* virp, Instruction_t* first, string dataBits, Instruction_t *target);
+Instruction_t* insertDataBitsAfter(FileIR_t* virp, Instruction_t* first, string dataBits);
+
+// add new instructions of diff types.
+Instruction_t* addNewDatabits(FileIR_t* firp, Instruction_t *p_instr, string p_bits);
+Instruction_t* addNewAssembly(FileIR_t* firp, Instruction_t *p_instr, string p_asm);
+
+
+//Does not insert into any variant, just copies data about the instruction itself, see the copyInstruction(src,dest) to see what is copied. 
+Instruction_t* copyInstruction(Instruction_t* instr);
+
+Instruction_t* copyInstruction(FileIR_t* virp, Instruction_t* instr);
+//copy src to destination
+void copyInstruction(Instruction_t* src, Instruction_t* dest);
+
+Instruction_t* allocateNewInstruction(FileIR_t* virp, DatabaseID_t p_fileID,Function_t* func);
+Instruction_t* allocateNewInstruction(FileIR_t* virp, Instruction_t *template_instr);
+void setInstructionAssembly(FileIR_t* virp,Instruction_t *p_instr, string p_assembly, Instruction_t *p_fallThrough, Instruction_t *p_target);
+
+
+}
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform.cpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b72c5f7941fc2a8a4f5ff688466dabf2bc06c415
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform.cpp
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <assert.h>
+#include "integertransform.hpp"
+#include "leapattern.hpp"
+
+
+/*
+ * Find the first occurrence of find in s, ignore case.
+ */
+static char *
+my_strcasestr(const char* s, const char *find)
+{
+        char c, sc;
+        size_t len;
+
+        if ((c = *find++) != 0) {
+                c = tolower((unsigned char)c);
+                len = strlen(find);
+                do {
+                        do {
+                                if ((sc = *s++) == 0)
+                                        return (NULL);
+                        } while ((char)tolower((unsigned char)sc) != c);
+                } while (strncasecmp(s, find, len) != 0);
+                s--;
+        }
+        return ((char *)s);
+}
+
+
+// 
+// For list of blacklisted functions, see: isBlacklisted()
+//
+
+using namespace libTransform;
+
+IntegerTransform::IntegerTransform(VariantID_t *p_variantID, FileIR_t *p_fileIR, 
+// std::multimap<VirtualOffset, MEDS_AnnotationBase> 
+MEDS_Annotations_t *p_annotations, 
+set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_benignFalsePositives) : Transform(p_variantID, p_fileIR, p_filteredFunctions) 
+{
+	m_benignFalsePositives = p_benignFalsePositives;
+	m_policySaturatingArithmetic = false;
+	m_policyWarningsOnly = false;
+	m_pathManipulationDetected = false;
+	m_instrumentIdioms = false;
+
+	m_annotations = p_annotations;              
+
+	m_numAnnotations = 0;
+	m_numIdioms = 0;
+	m_numBlacklisted = 0;
+	m_numBenign = 0;
+	m_numFP = 0;
+
+	m_numTotalOverflows = 0;
+	m_numTotalUnderflows = 0;
+	m_numTotalTruncations = 0;
+	m_numTotalSignedness = 0;
+
+	m_numOverflows = 0;
+	m_numUnderflows = 0;
+	m_numTruncations = 0;
+	m_numSignedness = 0;
+
+	m_numOverflowsSkipped = 0;
+	m_numUnderflowsSkipped = 0;
+	m_numTruncationsSkipped = 0;
+	m_numSignednessSkipped = 0;
+
+	m_instrumentSP = false;
+	m_instrumentFP = false;
+}
+
+bool IntegerTransform::isBlacklisted(Function_t *func)
+{
+	if (!func) return false;
+
+	const char *funcName = func->GetName().c_str();
+	return (my_strcasestr(funcName, "hash") ||
+		my_strcasestr(funcName, "compress") ||
+		my_strcasestr(funcName, "encode") ||
+		my_strcasestr(funcName, "decode") ||
+		my_strcasestr(funcName, "crypt") ||
+		my_strcasestr(funcName, "yyparse") ||
+		my_strcasestr(funcName, "yyerror") ||
+		my_strcasestr(funcName, "yydestruct") ||
+		my_strcasestr(funcName, "yyrestart") ||
+		my_strcasestr(funcName, "yylex") ||
+		my_strcasestr(funcName, "yyparse") ||
+		my_strcasestr(funcName, "yyerror") ||
+		my_strcasestr(funcName, "yydestruct") ||
+		my_strcasestr(funcName, "yyrestart") ||
+		my_strcasestr(funcName, "yylex") ||
+		my_strcasestr(funcName, "yy_"));
+}
+
+void IntegerTransform::logStats()
+{
+	std::string fileURL = getFileIR()->GetFile()->GetURL();	
+
+	std::cerr << "# ATTRIBUTE intx::file_name=" << fileURL << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_annotations_processed=" << dec << m_numAnnotations << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_idioms=" << m_numIdioms << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_blacklisted=" << m_numBlacklisted << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_benign=" << m_numBenign << std::endl;
+
+	std::cerr << "# ATTRIBUTE intx::num_total_overflows=" << m_numTotalOverflows << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_overflows_instrumented=" << m_numOverflows << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_overflows_skipped=" << m_numOverflowsSkipped << std::endl;
+	std::cerr << "# ATTRIBUTE intx::overflows_coverage=" << (double)m_numOverflows/(double)m_numTotalOverflows << std::endl;
+
+	std::cerr << "# ATTRIBUTE intx::num_total_underflows=" << m_numTotalUnderflows << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_underflows_instrumented=" << m_numUnderflows << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_underflows_skipped=" << m_numUnderflowsSkipped << std::endl;
+	std::cerr << "# ATTRIBUTE intx::underflows_coverage=" << (double)m_numUnderflows/(double)m_numTotalUnderflows << std::endl;
+
+	std::cerr << "# ATTRIBUTE intx::num_total_truncations=" << m_numTotalTruncations << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_truncations_instrumented=" << m_numTruncations << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_truncations_skipped=" << m_numTruncationsSkipped << std::endl;
+	std::cerr << "# ATTRIBUTE intx::truncation_coverage=" << (double)m_numTruncations/(double)m_numTotalTruncations << std::endl;
+
+	std::cerr << "# ATTRIBUTE intx::num_total_signedness=" << m_numTotalSignedness << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_signedness_instrumented=" << m_numSignedness << std::endl;
+	std::cerr << "# ATTRIBUTE intx::num_signedness_skipped=" << m_numSignednessSkipped << std::endl;
+	std::cerr << "# ATTRIBUTE intx::signedness_coverage=" << (double)m_numSignedness/(double)m_numTotalSignedness << std::endl;
+
+	std::cerr << "# ATTRIBUTE intx::num_floating_point=" << m_numFP << std::endl;
+}
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..ce9e5f361147bfff01d5ee0bb31a25dcc7138724
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform.hpp
@@ -0,0 +1,99 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef _LIBTRANSFORM_INTEGERTRANSFORM_H_
+#define _LIBTRANSFORM_INTEGERTRANSFORM_H_
+
+#include "transform.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_AnnotationParser.hpp"
+#include "VirtualOffset.hpp"
+
+namespace libTransform
+{
+
+using namespace std;
+using namespace libIRDB;
+
+const int IDIOM_POINTER_NUMERIC_WEAKNESS = 18;
+
+class IntegerTransform : public Transform
+{
+	public:
+		IntegerTransform(VariantID_t *, FileIR_t*, MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_warnings); 
+		virtual int execute() = 0;
+
+		void setSaturatingArithmetic(bool p_satArithmetic) { m_policySaturatingArithmetic = p_satArithmetic; }
+		bool isSaturatingArithmetic() { return m_policySaturatingArithmetic; }
+		void setPathManipulationDetected(bool p_pathManip) { m_pathManipulationDetected = p_pathManip; }
+		bool isPathManipulationDetected() { return m_pathManipulationDetected; }
+		void setWarningsOnly(bool p_warn) { m_policyWarningsOnly = p_warn; }
+		bool isWarningsOnly() { return m_policyWarningsOnly; }
+		void setInstrumentIdioms(bool p_idioms) { m_instrumentIdioms = p_idioms; }
+		bool isInstrumentIdioms() { return m_instrumentIdioms; }
+		void logStats();
+		bool isBlacklisted(Function_t *func);
+	
+	protected:
+		void setInstrumentSP(bool sp) { m_instrumentSP = sp; }
+		bool instrumentSP() const { return m_instrumentSP; } 
+		void setInstrumentFP(bool fp) { m_instrumentFP = fp; }
+		bool instrumentFP() const { return m_instrumentFP; } 
+
+	protected:
+		MEDS_Annotations_t* getAnnotations() { return m_annotations; }
+
+		std::set<VirtualOffset>*  m_benignFalsePositives;
+		bool                      m_policySaturatingArithmetic;
+		bool                      m_policyWarningsOnly;
+		bool                      m_pathManipulationDetected;
+		bool                      m_instrumentIdioms;
+		MEDS_Annotations_t *m_annotations;
+
+		unsigned m_numAnnotations; 
+		unsigned m_numIdioms; 
+		unsigned m_numBlacklisted; 
+		unsigned m_numBenign; 
+
+		unsigned m_numTotalOverflows; 
+		unsigned m_numOverflows; 
+		unsigned m_numOverflowsSkipped; 
+
+		unsigned m_numTotalUnderflows; 
+		unsigned m_numUnderflows; 
+		unsigned m_numUnderflowsSkipped; 
+
+		unsigned m_numTotalTruncations; 
+		unsigned m_numTruncations; 
+		unsigned m_numTruncationsSkipped; 
+
+		unsigned m_numTotalSignedness; 
+		unsigned m_numSignedness; 
+		unsigned m_numSignednessSkipped; 
+
+		unsigned m_numFP; 
+
+		bool m_instrumentSP;
+		bool m_instrumentFP;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform32.cpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform32.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3f63ef75561fff2b9d8086393e3ec25ac69819b5
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform32.cpp
@@ -0,0 +1,2175 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <assert.h>
+#include "integertransform32.hpp"
+#include "leapattern.hpp"
+
+// 
+// For list of blacklisted functions, see: isBlacklisted()
+//
+
+//
+// MEDS has the following annotation types:
+//     - OVERFLOW (SIGNED|UNSIGNED|UNKNOWN) (32,16,8)
+//     - UNDERFLOW (SIGNED|UNSIGNED|UNKNOWN) (32,16,8)
+//     - SIGNEDNESS SIGNED (32,16,8)
+//     - TRUNCATION (SIGNED|UNSIGNED|UNKNOWN) (32,16,8)
+//     - XXX_NOFLAG (Many forms, handles LEA)
+//
+// Saturating arithmetic implemented for:
+//      - OVERFLOW (when destination is a register)
+//      - UNDERFLOW (when destination is a register)
+//      - SIGNEDNESS 
+//      - TRUNCATION
+//
+// ============= TO DO ============= 
+// Saturating arithmetic to do:
+//      - OVERFLOW (dest. is not a register)
+//      - UNDERFLOW (dest. is not a register)
+//
+// Instrumentation:
+//      - TRUNCATION (16->8)   no test cases available
+//      - LEA                  only reg32+reg32 case implemented
+// 20130409 Anh  fixed lea reg+reg bug (we were assuming that annotation matched instruction exactly)
+// 20130410 Anh  implemented shared library support -- added outer loop to iterate over all files in the driver program
+// 20130411 Anh  skip instrumentation where there's no fallthrough for an instruction
+//
+using namespace libTransform;
+
+IntegerTransform32::IntegerTransform32(VariantID_t *p_variantID, FileIR_t *p_fileIR, 
+MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_benignFalsePositives) : IntegerTransform(p_variantID, p_fileIR, p_annotations, p_filteredFunctions, p_benignFalsePositives)
+{
+}
+
+// iterate through all functions
+// filter those functions that should be ignored
+//    iterate through all instructions in function
+//    if MEDS annotation says to instrument
+//       add instrumentation
+int IntegerTransform32::execute()
+{
+	if (isSaturatingArithmetic())
+		cerr << "IntegerTransform32: Saturating Arithmetic is enabled" << endl;
+	else
+		cerr << "IntegerTransform32: Saturating Arithmetic is disabled" << endl;
+
+	if (isPathManipulationDetected())
+		cerr << "IntegerTransform32: Exit on truncation" << endl;
+
+	if (isWarningsOnly())
+		cerr << "IntegerTransform32: Warnings only mode" << endl;
+
+	for(
+	  set<Function_t*>::const_iterator itf=getFileIR()->GetFunctions().begin();
+	  itf!=getFileIR()->GetFunctions().end();
+	  ++itf
+	  )
+	{
+		Function_t* func=*itf;
+
+		if (getFilteredFunctions()->find(func->GetName()) != getFilteredFunctions()->end())
+		{
+			continue;
+		}
+
+		if (isBlacklisted(func))
+		{
+			cerr << "Heuristic filter: " << func->GetName() << endl;
+			m_numBlacklisted++;
+			continue;
+		}
+
+		logMessage(__func__, "processing fn: " + func->GetName());
+
+		for(
+		  set<Instruction_t*>::const_iterator it=func->GetInstructions().begin();
+		  it!=func->GetInstructions().end();
+		  ++it)
+		{
+			Instruction_t* insn=*it;
+
+			if (insn && insn->getAddress())
+			{
+				int policy = POLICY_DEFAULT; // use Strata default settings
+				virtual_offset_t irdb_vo = insn->getAddress()->GetVirtualOffset();
+				if (irdb_vo == 0) continue;
+
+				VirtualOffset vo(irdb_vo);
+
+				if(insn->GetDataBits().c_str()[0]==(char)0xDF || insn->GetDataBits().c_str()[0]==(char)0xDB){
+                    handleFISTTruncation(insn);
+                }
+                
+				if (isSaturatingArithmetic())
+				{
+					// saturating arithmetic is enabled
+					// only use if instruction is not a potential false positive
+					policy = POLICY_CONTINUE_SATURATING_ARITHMETIC;
+				}
+
+				// takes precedence over saturation if conflict
+				if (isWarningsOnly())
+				{
+					policy = POLICY_CONTINUE;
+				}
+
+				// overwrite the above if needed
+				if (isPathManipulationDetected())
+				{
+					policy = POLICY_EXIT;
+				}
+
+				if (m_benignFalsePositives && m_benignFalsePositives->count(vo))
+				{
+					// potential benign false positives
+					m_numBenign++;
+					policy = POLICY_CONTINUE;
+				}
+
+
+/*
+				MEDS_InstructionCheckAnnotation annotation = (*getAnnotations())[vo];
+				if (!annotation.isValid()) 
+					continue;
+*/
+                                if (getAnnotations()->count(vo) == 0)
+                                        continue;
+
+                                std::pair< MEDS_Annotations_t::iterator, MEDS_Annotations_t::iterator > ret;
+                                ret = getAnnotations()->equal_range(vo);
+                                MEDS_InstructionCheckAnnotation annotation;
+                                MEDS_InstructionCheckAnnotation* p_annotation;
+                                for ( MEDS_Annotations_t::iterator it = ret.first; it != ret.second; ++it)
+                                {
+                                        MEDS_AnnotationBase *b = (it->second);
+					p_annotation=dynamic_cast<MEDS_InstructionCheckAnnotation*>(b);
+					if(!p_annotation)
+						continue;
+					annotation=*p_annotation;
+                                        if (!annotation.isValid())
+                                                continue;
+                                        else
+                                                break; // let's just handle one annotation for now and see how it goes
+                                }
+
+				if (!annotation.isValid()) 
+					continue;
+
+				logMessage(__func__, annotation, "-- instruction: " + insn->getDisassembly());
+				m_numAnnotations++;
+
+				if (annotation.isIdiom())
+				{
+					logMessage(__func__, "skip IDIOM");
+					m_numIdioms++;
+					continue;
+				}
+
+				if (!insn->getFallthrough())
+				{
+					logMessage(__func__, "Warning: no fall through for instruction -- skipping");
+					continue;
+				}
+
+				if (annotation.isOverflow())
+				{
+					// nb: safe with respect to esp (except for lea)
+					m_numTotalOverflows++;
+					handleOverflowCheck(insn, annotation, policy);
+				}
+				else if (annotation.isUnderflow() && !annotation.isNoFlag())
+				{
+					m_numTotalUnderflows++;
+					// nb: safe with respect to esp
+					handleUnderflowCheck(insn, annotation, policy);
+				}
+				else if (annotation.isTruncation())
+				{
+					m_numTotalTruncations++;
+					handleTruncation(insn, annotation, policy);
+				}
+				else if (annotation.isSignedness())
+				{
+					m_numTotalSignedness++;
+					if (annotation.isUnknownSign())
+					{
+						logMessage(__func__, "annotation has unknown sign: skipping");
+						continue;
+					}
+					handleSignedness(insn, annotation, policy);
+				}
+				else if (annotation.isInfiniteLoop())
+				{
+					handleInfiniteLoop(insn, annotation, POLICY_EXIT);
+				}
+				else
+				{
+					logMessage(__func__, "unknown annotation");
+				}
+			}
+		} // end iterate over all instructions in a function
+	} // end iterate over all functions
+
+	return 0;
+}
+
+void IntegerTransform32::handleSignedness(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	if (p_annotation.isSigned() || p_annotation.isUnsigned())
+		addSignednessCheck(p_instruction, p_annotation, p_policy);
+	else
+		logMessage(__func__, "case not yet handled");
+}
+
+// 8048576 5 INSTR CHECK SIGNEDNESS SIGNED 16 AX ZZ mov     [esp+28h], ax
+//             <save flags>
+//             TEST ax, ax
+//             jns L1
+//             invoke conversion handler
+// (optional)  mov ax, MAX_16     ; saturating arithmetic (Max for bit width/sign/unsigned) 
+//  
+//       L1:   <restore flags>
+//             mov [esp+28h], ax
+//
+// 20120414 We may want to saturate the destination instead. This would mean putting the saturation code
+//          after the instruction being instrumented
+void IntegerTransform32::addSignednessCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	// sanity checks
+    assert(getFileIR() && p_instruction);
+	assert (p_annotation.isValid());
+	if (
+		!(p_annotation.getBitWidth() == 32 && Register::is32bit(p_annotation.getRegister())) && 
+		!(p_annotation.getBitWidth() == 16 && (Register::is16bit(p_annotation.getRegister()) ||
+			p_annotation.getRegister() == rn_ESI || p_annotation.getRegister() == rn_EDI || p_annotation.getRegister() == rn_EBP)) && 
+		!(p_annotation.getBitWidth() == 8 && Register::is8bit(p_annotation.getRegister())) 
+		)
+	{
+		logMessage(__func__, "unexpected bit width and register combination: skipping");
+		m_numSignednessSkipped++;
+	  return;
+	}
+
+    DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+    Function_t* func = p_instruction->GetFunction();
+
+	Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* test_i = allocateNewInstruction(fileID, func);
+	Instruction_t* jns_i = allocateNewInstruction(fileID, func);
+	Instruction_t* nop_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+
+	addPushf(pushf_i, test_i);
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pushf_i);
+	pushf_i->setFallthrough(test_i); 
+	pushf_i->setComment("-- in signedness check");
+	addTestRegister(test_i, p_annotation.getRegister(), jns_i);
+	addJns(jns_i, nop_i, popf_i);
+	addNop(nop_i, popf_i);
+
+	string detector;
+	if (p_annotation.getBitWidth() == 32)
+		detector = string(SIGNEDNESS_DETECTOR_32);
+	else if (p_annotation.getBitWidth() == 16)
+		detector = string(SIGNEDNESS_DETECTOR_16);
+	else if (p_annotation.getBitWidth() == 8)
+		detector = string(SIGNEDNESS_DETECTOR_8);
+
+	// sanity filter
+	if (p_annotation.getRegister() == rn_UNKNOWN)
+		p_policy = POLICY_DEFAULT;
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		// implement saturating arithmetic on register, i.e.: mov <reg>, value
+		Instruction_t* saturate_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+
+		addCallbackHandler(detector, originalInstrumentInstr, nop_i, saturate_i, p_policy, p_instruction->getAddress());
+		if (p_annotation.isSigned())
+			addMaxSaturation(saturate_i, p_annotation.getRegister(), p_annotation, popf_i);
+		else
+			addZeroSaturation(saturate_i, p_annotation.getRegister(), popf_i);
+	}
+	else
+	{
+		addCallbackHandler(detector, originalInstrumentInstr, nop_i, popf_i, p_policy, p_instruction->getAddress());
+	}
+	addPopf(popf_i, originalInstrumentInstr);
+
+	m_numSignedness++;
+}
+
+void IntegerTransform32::handleOverflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	if (p_annotation.isUnknownSign() && !p_annotation.isNoFlag())
+	{
+		addOverflowCheckUnknownSign(p_instruction, p_annotation, p_policy);
+	}
+	else if (p_annotation.isNoFlag())
+	{
+		// handle lea
+		addOverflowCheckNoFlag(p_instruction, p_annotation, p_policy);
+	}
+	else if (isMultiplyInstruction(p_instruction) || p_annotation.isUnderflow() || p_annotation.isOverflow())
+	{
+		// handle signed/unsigned add/sub overflows (non lea)
+		addOverflowCheck(p_instruction, p_annotation, p_policy);
+	}
+	else
+	{
+		m_numOverflowsSkipped++;
+		logMessage(__func__, "OVERFLOW type not yet handled");
+	}
+}
+
+void IntegerTransform32::handleUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	if (p_annotation.isUnderflow())
+	{
+		addUnderflowCheck(p_instruction, p_annotation, p_policy);
+	}
+	else
+	{
+		m_numUnderflowsSkipped++;
+		logMessage(__func__, "UNDERFLOW type not yet handled");
+	}
+}
+
+/*
+   NOFLAGUNKNOWNSIGN 32 ESI+EDX ZZ lea     eax, [esi+edx] 
+   NOFLAGUNSIGNED 32 EDX+ESI+1900 ZZ lea     esi, [edx+esi+76Ch] 
+   NOFLAGUNSIGNED 32 EAX+382 ZZ lea     esi, [eax+17Eh] 
+   NOFLAGUNKNOWNSIGN 32 EDX*8 ZZ lea     eax, ds:0[edx*8] 
+   NOFLAGUNSIGNED 32 ECX+ECX*4 ZZ lea     ebx, [ecx+ecx*4] 
+   NOFLAGUNSIGNED 32 EDI+-66 ZZ lea     eax, [edi-42h] 
+   NOFLAGSIGNED 32 ESI+100 ZZ lea     ecx, [esi+64h] 
+
+   possible patterns after the bit width field:
+     rpr:  <reg>+<reg>
+	 rpc:  <reg>+-<constant>
+	 rpc:  <reg>+<constant>
+     rtc:  <reg>*constant
+
+
+   not yet handling these:
+     rprpc:  <reg>+<reg>+<constant>
+     rprpc:  <reg>+<reg>+-<constant>
+     rprtc:  <reg>+<reg>*<constant>
+*/
+void IntegerTransform32::addOverflowCheckNoFlag(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	LEAPattern leaPattern(p_annotation);
+
+	if (!leaPattern.isValid())
+	{
+		logMessage(__func__, "invalid or unhandled lea pattern - skipping: ");
+		m_numOverflowsSkipped++;
+		return;
+	}
+	
+	if (leaPattern.getRegister1() == rn_UNKNOWN ||
+		leaPattern.getRegister1() == rn_ESP ||
+		leaPattern.getRegister1() == rn_EBP)
+	{
+		logMessage(__func__, "destination register is unknown, esp or ebp -- skipping: ");
+		m_numOverflowsSkipped++;
+		return;
+	}
+	
+	if (leaPattern.isRegisterPlusRegister())
+	{
+		RegisterName reg1 = leaPattern.getRegister1();
+		RegisterName reg2 = leaPattern.getRegister2();
+		RegisterName target = getTargetRegister(p_instruction);
+
+		if (reg1 == rn_UNKNOWN || reg2 == rn_UNKNOWN || target == rn_UNKNOWN)
+		{
+			logMessage(__func__, "lea reg+reg pattern: error retrieving register: reg1: " + Register::toString(reg1) + " reg2: " + Register::toString(reg2) + " target: " + Register::toString(target));
+			m_numOverflowsSkipped++;
+			return;
+		}
+		else if (reg2 == rn_ESP) 
+		{
+			logMessage(__func__, "source register is esp -- skipping: ");
+			m_numOverflowsSkipped++;
+			return;
+		}
+		else
+		{
+			addOverflowCheckNoFlag_RegPlusReg(p_instruction, p_annotation, reg1, reg2, target, p_policy);
+		}
+	}
+	else if (leaPattern.isRegisterPlusConstant())
+	{
+		RegisterName reg1 = leaPattern.getRegister1();
+		int value = leaPattern.getConstant();
+		RegisterName target = getTargetRegister(p_instruction);
+
+		if (p_annotation.isUnsigned() && value < 0)
+		{
+			logMessage(__func__, "lea reg+neg constant pattern: skip this annotation type (prone to false positives)");
+			m_numOverflowsSkipped++;
+			return;
+		}
+		else if (reg1 == rn_UNKNOWN || target == rn_UNKNOWN)
+		{
+			logMessage(__func__, "lea reg+constant pattern: error retrieving register: reg1: " + Register::toString(reg1) + " target: " + Register::toString(target));
+			m_numOverflowsSkipped++;
+			return;
+		}
+		else
+		{
+			addOverflowCheckNoFlag_RegPlusConstant(p_instruction, p_annotation, reg1, value, target, p_policy);
+		}
+	}
+	else if (leaPattern.isRegisterTimesConstant())
+	{
+		RegisterName reg1 = leaPattern.getRegister1();
+		int value = leaPattern.getConstant();
+		RegisterName target = getTargetRegister(p_instruction);
+
+		if (reg1 == rn_UNKNOWN || target == rn_UNKNOWN)
+		{
+			logMessage(__func__, "lea reg*constant pattern: error retrieving register: reg1: " + Register::toString(reg1) + " target: " + Register::toString(target));
+			m_numOverflowsSkipped++;
+			return;
+		}
+		else
+		{
+			m_numOverflowsSkipped++;
+			addOverflowCheckNoFlag_RegTimesConstant(p_instruction, p_annotation, reg1, value, target, p_policy);
+		}
+	}
+	else
+	{
+		logMessage(__func__, "pattern not yet handled");
+		m_numOverflowsSkipped++;
+		return;
+	}
+}
+
+// Example annotation to handle
+// 804852e      3 INSTR CHECK OVERFLOW NOFLAGSIGNED 32 EDX+EAX ZZ lea     eax, [edx+eax] Reg1: EDX Reg2: EAX
+void IntegerTransform32::addOverflowCheckNoFlag_RegPlusReg(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const RegisterName& p_reg2, const RegisterName& p_reg3, int p_policy)
+{
+	cerr << __func__ << ": reg+constant: r1: " << Register::toString(p_reg1) << " r2: " << Register::toString(p_reg2) << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	//   orig:  lea r3, [r1+r2]
+	//   <originalNext>
+	//
+	// Instrumentation:
+	//   push r1                ;   save r1
+	//   pushf                  ;   save flags
+	//   add r1, r2             ;   r1 = r1 + r2
+	//        <overflowcheck>   ;   check for overflow as dictated by annotation
+	//          (jno|jnc <restore>)    ; SIGNED|UNSIGNED
+	//            fallthrough--><saturate>
+	//          (jno&jnc <restore>)    ; UNKNOWNSIGN both flags  
+	//            fallthrough--><saturate>
+	//
+	// <restore>
+	//          popf                   ; restore flags
+	//          pop r1                 ; restore register
+	//
+	// <orig>:  lea r3, [r1+r2]        ; original instruction        
+	//         <originalNext>          ; original next instruction
+	//
+	// <saturate>                      ; optional saturation code
+	//         popf                    ; restore flags
+	//         pop r1                  ; restore register
+	//         saturateMax(r3)         ; 
+	//            fallthrough-->originalNext
+	//
+
+	DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+
+	Instruction_t* pushr1_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* addRR_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popr1_i = allocateNewInstruction(fileID, func);
+
+	// reuse annotation info when checking for overflow
+	MEDS_InstructionCheckAnnotation addRR_annot;
+	addRR_annot.setValid();
+	addRR_annot.setBitWidth(32);
+	addRR_annot.setOverflow();
+	if (p_annotation.isSigned())
+		addRR_annot.setSigned();
+	else if (p_annotation.isUnsigned())
+		addRR_annot.setUnsigned();
+	else
+		addRR_annot.setUnknownSign();
+
+	string msg = "Originally: " + p_instruction->getDisassembly();
+	Instruction_t* originalNextInstr = p_instruction->getFallthrough();
+	AddressID_t *originalAddress = p_instruction->getAddress();
+
+	addPushRegister(pushr1_i, p_reg1, pushf_i);
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pushr1_i);
+	pushr1_i->setFallthrough(pushf_i);
+	pushr1_i->setComment("-- carefullyInsertBefore NoFlagRegPlusReg");
+
+	addPushf(pushf_i, addRR_i);
+
+	addAddRegisters(addRR_i, p_reg1, p_reg2, popf_i);
+	addRR_i->setComment(msg);
+
+	addPopf(popf_i, popr1_i);
+	addPopRegister(popr1_i, p_reg1, originalInstrumentInstr);
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+	//   add r1, r2             ;   r1 = r1 + r2
+	//          (jno|jnc <restore>)    ; SIGNED|UNSIGNED
+	//            fallthrough--><saturate>
+	//          (jno&jnc <restore>)    ; UNKNOWNSIGN both flags  
+	//            fallthrough--><saturate>
+	//
+	// <restore>
+	//          popf                   ; restore flags
+	//          pop r1                 ; restore register
+	//
+	// <orig>:  lea r3, [r1+r2]        ; original instruction        
+	//         <originalNext>          ; original next instruction
+	//
+	// <saturate>                      ; optional saturation code
+	//         popf                    ; restore flags
+	//         pop r1                  ; restore register
+	//         saturateMax(r3)         ; 
+	//            fallthrough-->originalNext
+
+		Instruction_t* j_i = allocateNewInstruction(fileID, func);
+		Instruction_t* jnc_i = NULL;
+		Instruction_t* popfsat_i = allocateNewInstruction(fileID, func);
+		Instruction_t* popR1sat_i = allocateNewInstruction(fileID, func);
+		Instruction_t* saturate_i = allocateNewInstruction(fileID, func);
+
+		addRR_i->setFallthrough(j_i);
+	
+		if (p_annotation.isSigned())
+		{
+			addJno(j_i, popfsat_i, popf_i);
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			addJnc(j_i, popfsat_i, popf_i);
+		}
+		else
+		{
+			jnc_i = allocateNewInstruction(fileID, func);
+			addJno(j_i, jnc_i, popf_i);
+			addJnc(jnc_i, popfsat_i, popf_i);
+		}
+
+		addOverflowCheckForLea(addRR_i, addRR_annot, p_policy, originalAddress);
+
+		addPopf(popfsat_i, popR1sat_i);
+		addPopRegister(popR1sat_i, p_reg1, saturate_i);
+		addMaxSaturation(saturate_i, p_reg3, p_annotation, originalNextInstr);
+	}
+	else
+	{
+		addOverflowCheckForLea(addRR_i, addRR_annot, p_policy, originalAddress);
+	}
+
+	m_numOverflows++;
+}
+
+void IntegerTransform32::addOverflowCheckNoFlag_RegPlusConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const int p_constantValue, const RegisterName& p_reg3, int p_policy)
+{
+	if (!p_instruction)
+		return;
+
+	if (p_instruction->GetIndirectBranchTargetAddress())
+		cerr << "IBTA set: ";
+	else
+		cerr << "no IBTA: ";
+
+	cerr << __func__ << ": reg+constant: register: " << Register::toString(p_reg1) << " constant: " << dec << p_constantValue << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	//
+	// Original instruction is of the form:
+	//   lea r3, [r1+constant]          
+	//   lea r3, [r1-constant]          
+	//   <originalNext>
+	//
+	// Example annotation:
+	//   8049410 3 INSTR CHECK OVERFLOW NOFLAGUNSIGNED 32 EAX+-15 ZZ lea ebx, [eax-0Fh]
+	//
+	// In this example:
+	//   r3 = ebx
+	//   r1 = eax
+	//   constant = -15
+	//
+	// Instrumentation:
+	//          push r3                ; save register
+	//          pushf                  ; save flags
+	//          mov r3, r1             ; r3 = r1
+	//          add r3, constant       ; r3 = r1 + constant;
+	//              <overflowCheck>    ; reuse overflow code
+	//          (jno|jnc <restore>)    ; SIGNED|UNSIGNED
+	//            fallthrough--><saturate>
+	//          (jno&jnc <restore>)    ; UNKNOWNSIGN both flags  
+	//            fallthrough--><saturate>
+	// <restore>
+	//          popf                   ; restore flags
+	//          pop r3                 ; restore register
+	//
+	//          
+	// <orig>:  lea r3, [r1+constant]  ; original instruction        
+	//         <originalNext>          ; original next instruction
+	//                                 
+	// <saturate>                      ; optional saturation code
+	//         popf                    ; restore flags
+	//         pop r3                  ; restore register
+	//         saturateMax(r3)         ; 
+	//            fallthrough-->originalNext
+	//
+	//
+	// Note: if r3 == r1, code still works (though inefficiently)
+	//
+
+	DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+
+	Instruction_t* pushR3_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* movR3R1_i = allocateNewInstruction(fileID, func);
+	Instruction_t* addR3Constant_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popR3_i = allocateNewInstruction(fileID, func);
+
+	MEDS_InstructionCheckAnnotation addR3Constant_annot;
+	addR3Constant_annot.setValid();
+	addR3Constant_annot.setBitWidth(32);
+	addR3Constant_annot.setOverflow();
+	if (p_annotation.isSigned())
+		addR3Constant_annot.setSigned();
+	else if (p_annotation.isUnsigned())
+		addR3Constant_annot.setUnsigned();
+	else
+		addR3Constant_annot.setUnknownSign();
+
+	string msg = "Originally: " + p_instruction->getDisassembly();
+	Instruction_t* originalNextInstr = p_instruction->getFallthrough();
+
+	AddressID_t *originalAddress = p_instruction->getAddress();
+
+	addPushRegister(pushR3_i, p_reg3, pushf_i);
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pushR3_i);
+	pushR3_i->setComment("in lea -- RegPlusConstant");
+	pushR3_i->setFallthrough(pushf_i);  
+	addPushf(pushf_i, movR3R1_i);
+
+	addMovRegisters(movR3R1_i, p_reg3, p_reg1, addR3Constant_i);
+	addAddRegisterConstant(addR3Constant_i, p_reg3, p_constantValue, popf_i);
+	addPopf(popf_i, popR3_i);
+	addPopRegister(popR3_i, p_reg3, originalInstrumentInstr);
+
+	addR3Constant_i->setComment(msg);
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+	//          (jno|jnc <restore>)    ; SIGNED|UNSIGNED
+	//            fallthrough--><saturate>
+	//          (jno&jnc <restore>)    ; UNKNOWNSIGN both flags  
+	//            fallthrough--><saturate>
+	//
+	// <restore>
+	//          popf                   ; restore flags
+	//          pop r3                 ; restore register
+	//
+	// <saturate>
+	//         popf                   ; restore flags
+	//         pop r3                 ; restore register
+	//         saturateMax(r3)        ; 
+	//            fallthrough-->originalNext
+		Instruction_t* j_i = allocateNewInstruction(fileID, func);
+		Instruction_t* jnc_i = NULL;
+		Instruction_t* popfsat_i = allocateNewInstruction(fileID, func);
+		Instruction_t* popR3sat_i = allocateNewInstruction(fileID, func);
+		Instruction_t* saturate_i = allocateNewInstruction(fileID, func);
+
+		addR3Constant_i->setFallthrough(j_i);
+	
+		if (p_annotation.isSigned())
+		{
+			addJno(j_i, popfsat_i, popf_i);
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			addJnc(j_i, popfsat_i, popf_i);
+		}
+		else
+		{
+			jnc_i = allocateNewInstruction(fileID, func);
+			addJno(j_i, jnc_i, popf_i);
+			addJnc(jnc_i, popfsat_i, popf_i);
+		}
+
+		addOverflowCheckForLea(addR3Constant_i, addR3Constant_annot, p_policy, originalAddress);
+
+		addPopf(popfsat_i, popR3sat_i);
+		addPopRegister(popR3sat_i, p_reg3, saturate_i);
+		addMaxSaturation(saturate_i, p_reg3, p_annotation, originalNextInstr);
+	}
+	else
+	{
+		addOverflowCheckForLea(addR3Constant_i, addR3Constant_annot, p_policy, originalAddress);
+	}
+	m_numOverflows++;
+}
+
+void IntegerTransform32::addOverflowCheckNoFlag_RegTimesConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const int p_constantValue, const RegisterName& p_reg3, int p_policy)
+{
+	cerr << __func__ << ": reg*constant: register: " << Register::toString(p_reg1) << " constant: " << p_constantValue << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	//
+	// Original instruction is of the form:
+	//   lea r3, [r1*constant]          
+	//   <originalNext>
+	//
+	// Instrumentation:
+	//         push r3                ; save register
+	//         pushf                  ; save flags
+	//         mov r3, r1             ; r3 = r1
+	//         imul r3, constant      ; r3 = r1 * constant;
+	//           <overflowCheck>      ; emit diagnostics
+	//         (jo <saturate>)        ; optional saturation code
+	//         popf                   ; restore flags
+	//         pop r3                 ; restore register
+	//
+	// <orig>: lea r3, [r1*constant]  ; original instruction        
+	//         <originalNext>         ; original next instruction
+    //
+	// ; optional saturation code
+	// <saturate>
+	//         popf                   ; restore flags
+	//         pop r3                 ; restore register
+	//         saturateMax(r3)        ; 
+	//            fallthrough-->originalNext
+	//
+	// Note: if r3 == r1, code still works (though inefficiently)
+	//
+	DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+
+	Instruction_t* pushR3_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* movR3R1_i = allocateNewInstruction(fileID, func);
+	Instruction_t* mulR3Constant_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popR3_i = allocateNewInstruction(fileID, func);
+
+	MEDS_InstructionCheckAnnotation mulR3Constant_annot;
+	mulR3Constant_annot.setValid();
+	mulR3Constant_annot.setBitWidth(32); 
+	mulR3Constant_annot.setOverflow();
+	if (p_annotation.isSigned())
+		mulR3Constant_annot.setSigned();
+	else if (p_annotation.isUnsigned())
+		mulR3Constant_annot.setUnsigned();
+	else
+		mulR3Constant_annot.setUnknownSign();
+
+	string msg = "Originally: " + p_instruction->getDisassembly();
+	Instruction_t* originalNextInstr = p_instruction->getFallthrough();
+
+	AddressID_t *originalAddress = p_instruction->getAddress();
+
+	addPushRegister(pushR3_i, p_reg3, pushf_i);
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pushR3_i);
+	pushR3_i->setFallthrough(pushf_i);
+	pushR3_i->setComment("in lea -- Reg * Constant"); 
+	addPushf(pushf_i, movR3R1_i);
+
+	addMovRegisters(movR3R1_i, p_reg3, p_reg1, mulR3Constant_i);
+	addMulRegisterConstant(mulR3Constant_i, p_reg3, p_constantValue, popf_i);
+	addPopf(popf_i, popR3_i);
+	addPopRegister(popR3_i, p_reg3, originalInstrumentInstr);
+
+	mulR3Constant_i->setComment(msg);
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+	//         (jo <saturate>)        ; optional saturation code
+	//         popf                   ; restore flags
+	//
+	// <saturate>
+	//         popf                   ; restore flags
+	//         pop r3                 ; restore register
+	//         saturateMax(r3)        ; 
+	//            fallthrough-->originalNext
+		Instruction_t* jo_i = allocateNewInstruction(fileID, func);
+		Instruction_t* popfsat_i = allocateNewInstruction(fileID, func);
+		Instruction_t* popR3sat_i = allocateNewInstruction(fileID, func);
+		Instruction_t* saturate_i = allocateNewInstruction(fileID, func);
+
+		mulR3Constant_i->setFallthrough(jo_i);
+		addOverflowCheckForLea(mulR3Constant_i, mulR3Constant_annot, p_policy, originalAddress);
+	
+		addJo(jo_i, popf_i, popfsat_i);
+		addPopf(popfsat_i, popR3sat_i);
+		addPopRegister(popR3sat_i, p_reg3, saturate_i);
+		addMaxSaturation(saturate_i, p_reg3, p_annotation, originalNextInstr);
+	}
+	else
+	{
+		// fallthrough was set previously to popf_i
+		addOverflowCheckForLea(mulR3Constant_i, mulR3Constant_annot, p_policy, originalAddress);
+	}
+	m_numOverflows++;
+}
+
+
+void IntegerTransform32::handleFISTTruncation(Instruction_t *p_instruction){
+    cerr << "IntegerTransform32::handleFISTTruncation(): instr: " << p_instruction->getDisassembly() << " address: "
+    << p_instruction->getAddress() << endl;
+	int len=0;
+    
+	//We skip the qword case.
+	if(p_instruction->getDisassembly().find("qword")!=std::string::npos){
+		len = 64;
+	}
+	else if(p_instruction->getDisassembly().find("dword")!=std::string::npos){
+		len = 32;
+	}
+	else if(p_instruction->getDisassembly().find(" word")!=std::string::npos){
+		len = 16;
+	}
+	if(p_instruction->getDisassembly().substr(0,5)=="fistp"){
+		cerr << "IntegerTransform32::addFistpTruncationCheck(): instr: " << p_instruction->getDisassembly() << " len= "
+        << len << endl;
+		addFistpTruncationCheck(p_instruction, len);
+	}
+	else if (p_instruction->getDisassembly().substr(0,4)=="fist"){
+		cerr << "IntegerTransform32::addFistTruncationCheck(): instr: " << p_instruction->getDisassembly() << " len= "
+        << len << endl;
+		addFistTruncationCheck(p_instruction, len);
+	}
+}
+
+void IntegerTransform32::addFistpTruncationCheck(Instruction_t *p_instruction, int len){
+	if(len!=32 && len!=16) return;
+    DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+    string dataBits;
+    
+    //Fistp dword [esp+0x28];
+    
+    /*
+     pusha
+     pushf
+     sub esp, 0x70
+     fstp dword [esp]
+     fsave [esp+4]
+     push_ret //call some_func
+     frstor [esp+4]
+     test eax, 0
+     jz_eax_0 label0
+     
+     test eax, 1
+     jz_eax_1 label1
+     
+     label2:
+     add esp, 0x70
+     ;; negtive min
+     mov [esp+0x28], 0x80000000
+     
+     
+     label0:
+     
+     add esp, 0x70
+     popf
+     popa
+     Fistp dword [esp+0x28]
+     
+     label1: ;;positive max
+     add esp, 0x70
+     popf
+     popa
+     mov [esp+0x28], 0x7FFFFFFF
+     //fistp []
+     */
+    
+    Instruction_t* pusha_i = allocateNewInstruction(fileID, func);
+    Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+    Instruction_t* sub_esp_0x70 = allocateNewInstruction(fileID, func); //81 ec 70 00 00 00
+    Instruction_t* fst_esp = allocateNewInstruction(fileID, func);//d9 14 24
+    // fsave [esp+4]
+    Instruction_t* fsave_wait = allocateNewInstruction(fileID, func);//9b
+    Instruction_t* fsave_esp_4 = allocateNewInstruction(fileID, func);//dd 74 24 04
+    Instruction_t* pushretaddress = allocateNewInstruction(fileID, func);
+    Instruction_t* frstor_esp_4 = allocateNewInstruction(fileID, func);//dd 64 24 04
+    
+    Instruction_t* test_eax_0 = allocateNewInstruction(fileID, func);
+    Instruction_t* test_eax_1 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* jz_eax_0 = allocateNewInstruction(fileID, func);
+    Instruction_t* jz_eax_1 = allocateNewInstruction(fileID, func);
+    
+    
+    Instruction_t* add_esp_0x70_label0 = allocateNewInstruction(fileID, func); //81 c4 70 00 00 00
+    Instruction_t* add_esp_0x70_label1 = allocateNewInstruction(fileID, func);
+    Instruction_t* add_esp_0x70_label2 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* popf_label0 = allocateNewInstruction(fileID, func);
+    Instruction_t* popa_label0 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* popf_label1 = allocateNewInstruction(fileID, func);
+    Instruction_t* popa_label1 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* popf_label2 = allocateNewInstruction(fileID, func);
+    Instruction_t* popa_label2 = allocateNewInstruction(fileID, func);
+    Instruction_t* nop = allocateNewInstruction(fileID, func);
+    
+    
+    addPusha(pusha_i, pushf_i);//pusha
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pusha_i);
+	pusha_i->setFallthrough(pushf_i);
+    
+    addPushf(pushf_i, sub_esp_0x70);//pushf
+    
+    dataBits.resize(6);//sub esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xec;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    sub_esp_0x70->setFallthrough(fst_esp);
+    sub_esp_0x70->setDataBits(dataBits);
+    sub_esp_0x70->setComment(sub_esp_0x70->getDisassembly());
+	addInstruction(sub_esp_0x70, dataBits, fst_esp, NULL);
+    
+    dataBits.resize(3);//fst [esp]
+    dataBits[0] = 0xd9;
+    dataBits[1] = 0x14;
+    dataBits[2] = 0x24;
+    fst_esp->setFallthrough(fsave_esp_4);
+    fst_esp->setDataBits(dataBits);
+    fst_esp->setComment(fst_esp->getDisassembly());
+        addInstruction(fst_esp, dataBits, fsave_esp_4, NULL);
+    dataBits.resize(1);//fsave [esp+4]
+    dataBits[0] = 0x9b;
+    fsave_esp_4->setFallthrough(pushretaddress);
+    fsave_esp_4->setDataBits(dataBits);
+    fsave_esp_4->setComment(fsave_wait->getDisassembly());
+        addInstruction(fsave_wait, dataBits, fsave_esp_4, NULL);
+    dataBits.resize(4);
+    dataBits[0] = 0xdd;
+    dataBits[1] = 0x74;
+    dataBits[2] = 0x24;
+    dataBits[3] = 0x04;
+    fsave_esp_4->setFallthrough(pushretaddress);
+    fsave_esp_4->setDataBits(dataBits);
+    fsave_esp_4->setComment(fsave_esp_4->getDisassembly());
+        addInstruction(fsave_esp_4, dataBits, pushretaddress, NULL);
+    
+    virtual_offset_t AfterTheCheckerReturn = getAvailableAddress();
+	nop->getAddress()->SetVirtualOffset(AfterTheCheckerReturn);
+	nop->getAddress()->SetFileID(BaseObj_t::NOT_IN_DATABASE);
+    
+    dataBits.resize(5);//push return_address
+    dataBits[0] = 0x68;
+    virtual_offset_t *tmp;
+    tmp = (virtual_offset_t *) &dataBits[1];
+    *tmp = AfterTheCheckerReturn;
+    pushretaddress->setDataBits(dataBits);
+    pushretaddress->setComment(pushretaddress->getDisassembly());
+    pushretaddress->setFallthrough(nop);
+	
+    
+	dataBits.resize(1);//nop
+	dataBits[0] = 0x90;
+	nop->setDataBits(dataBits);
+	nop->setComment(nop->getDisassembly() + " -- with callback to floating number check") ;
+	nop->setFallthrough(frstor_esp_4);
+	nop->SetIndirectBranchTargetAddress(nop->getAddress());
+	if(len==32)
+        nop->SetCallback(string("FloatingRangeCheck32"));
+    else
+        nop->SetCallback(string("FloatingRangeCheck16"));
+    
+    dataBits.resize(4);//frstor [esp+4]
+    dataBits[0] = 0xdd;
+    dataBits[1] = 0x64;
+    dataBits[2] = 0x24;
+    dataBits[3] = 0x04;
+    frstor_esp_4->setDataBits(dataBits);
+    frstor_esp_4->setFallthrough(test_eax_0);
+    frstor_esp_4->setComment(frstor_esp_4->getDisassembly());
+    dataBits.resize(2);//test eax, eax
+    dataBits[0] = 0x85;
+    dataBits[1] = 0xC0;
+    test_eax_0->setDataBits(dataBits);
+    test_eax_0->setFallthrough(jz_eax_0);
+    addInstruction(test_eax_0, dataBits, jz_eax_0, NULL);
+    addJz(jz_eax_0, test_eax_1, add_esp_0x70_label0);
+    
+    
+    //label 0:
+    Instruction_t* jmpOriginalInst = allocateNewInstruction(fileID, func);
+    
+    dataBits.resize(6);//add esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xc4;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    add_esp_0x70_label0->setFallthrough(popf_label0);
+    add_esp_0x70_label0->setDataBits(dataBits);
+    add_esp_0x70_label0->setComment(add_esp_0x70_label0->getDisassembly());
+	addInstruction(add_esp_0x70_label0, dataBits, popf_label0, NULL);
+    
+    addPopf(popf_label0, popa_label0);
+    addPopa(popa_label0, jmpOriginalInst);
+    
+	
+	dataBits.resize(2);
+	dataBits[0] = 0xeb;
+	jmpOriginalInst->setComment("Jump to original Inst");
+	addInstruction(jmpOriginalInst,dataBits,NULL, originalInstrumentInstr);
+    
+    //label 1:
+    
+    dataBits.resize(5);//test eax, 1
+    dataBits[0] = 0xA9;
+    dataBits[1] = 0x01;
+    dataBits[2] = 0x00;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    test_eax_1->setDataBits(dataBits);
+    test_eax_1->setComment(test_eax_1->getDisassembly()) ;
+    test_eax_1->setFallthrough(jz_eax_1);
+    addInstruction(test_eax_1, dataBits, jz_eax_1, NULL);
+    addJz(jz_eax_1,  add_esp_0x70_label1, add_esp_0x70_label2);
+    
+    
+    dataBits.resize(6);//add esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xc4;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    add_esp_0x70_label1->setFallthrough(popf_label1);
+    add_esp_0x70_label1->setDataBits(dataBits);
+    add_esp_0x70_label1->setComment(add_esp_0x70_label1->getDisassembly());
+	addInstruction(add_esp_0x70_label1, dataBits, popf_label1, NULL);
+    addPopf(popf_label1, popa_label1);
+    
+    if(len==32){
+		Instruction_t* mov0x7FFFFFFF = allocateNewInstruction(fileID, func);
+		Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label1, mov0x7FFFFFFF);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x7FFFFFFF->Assemble("mov "+ addExpr + ", 0x7FFFFFFF");
+        mov0x7FFFFFFF->setComment(mov0x7FFFFFFF->getDisassembly());
+		addInstruction(mov0x7FFFFFFF, mov0x7FFFFFFF->GetDataBits(), fstpST0, NULL);
+		popa_label1->setComment("just before " + mov0x7FFFFFFF->getDisassembly());
+		
+		dataBits.resize(2);//fstp st(0)
+    	dataBits[0] = 0xDD;
+    	dataBits[1] = 0xD8;
+		fstpST0->setDataBits(dataBits);
+		fstpST0->setFallthrough(jmpOriginalInstNext);
+		addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+        
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    else{
+    	Instruction_t* mov0x7FFF = allocateNewInstruction(fileID, func);
+    	Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label1, mov0x7FFF);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x7FFF->Assemble("mov "+ addExpr + ", 0x7FFF");
+        mov0x7FFF->setComment(mov0x7FFF->getDisassembly());
+        
+		//mov0x7FFF->setFallthrough(fstpST0);
+		addInstruction(mov0x7FFF, mov0x7FFF->GetDataBits(), fstpST0, NULL);
+        
+		dataBits.resize(2);//fstp st(0)
+    	dataBits[0] = 0xDD;
+    	dataBits[1] = 0xD8;
+        
+		fstpST0->setDataBits(dataBits);
+		fstpST0->setFallthrough(jmpOriginalInstNext);
+		addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+		
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    
+    dataBits.resize(6);//add esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xc4;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    add_esp_0x70_label2->setFallthrough(popf_label2);
+    add_esp_0x70_label2->setDataBits(dataBits);
+    add_esp_0x70_label2->setComment(add_esp_0x70_label2->getDisassembly());
+    addInstruction(add_esp_0x70_label2, dataBits, popf_label2, NULL);
+    
+    addPopf(popf_label2, popa_label2);
+	if(len==32){
+		Instruction_t* mov0x80000000 = allocateNewInstruction(fileID, func);
+		Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label2, mov0x80000000);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x80000000->Assemble("mov "+ addExpr + ", 0x80000001");
+        mov0x80000000->setComment(mov0x80000000->getDisassembly());
+       	mov0x80000000->setFallthrough(fstpST0);
+		addInstruction(mov0x80000000, mov0x80000000->GetDataBits(), fstpST0, NULL);
+		
+		dataBits.resize(2);//fstp st(0)
+    	dataBits[0] = 0xDD;
+    	dataBits[1] = 0xD8;
+        
+		addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+        
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    else{
+    	Instruction_t* mov0x8000 = allocateNewInstruction(fileID, func);
+    	Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label2, mov0x8000);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x8000->Assemble("mov "+ addExpr + ", 0x8001");
+        mov0x8000->setComment(mov0x8000->getDisassembly());
+        
+		addInstruction(mov0x8000, mov0x8000->GetDataBits(), fstpST0, NULL);
+        
+		dataBits.resize(2);//fstp st(0)
+    	dataBits[0] = 0xDD;
+    	dataBits[1] = 0xD8;
+        
+		addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    
+	m_numFP++;
+	return;
+}
+
+void IntegerTransform32::addFistTruncationCheck(Instruction_t *p_instruction, int len){
+    if(len!=32 && len!=16) return;
+    DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+    string dataBits;
+    
+    //Fist dword [esp+0x28];
+    
+    /*
+     pusha
+     pushf
+     sub esp, 4
+     fstp dword [esp]
+     push_ret //call some_func
+     test eax, 0
+     jz_eax_0 label0
+     
+     test eax, 1
+     jz_eax_1 label1
+     
+     label2:
+     add esp, 4
+     ;; negtive min
+     mov [esp+0x28], 0x80000001
+     
+     
+     label0:
+     
+     add esp, 4
+     popf
+     popa
+     Fist dword [esp+0x28]
+     
+     label1: ;;positive max
+     add esp, 4
+     popf
+     popa
+     mov [esp+0x28], 0x7FFFFFFF
+   
+     */
+    
+    Instruction_t* pusha_i = allocateNewInstruction(fileID, func);
+    Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+    Instruction_t* sub_esp_0x70 = allocateNewInstruction(fileID, func); //81 ec 70 00 00 00
+    Instruction_t* fst_esp = allocateNewInstruction(fileID, func);//d9 14 24
+    // fsave [esp+4]
+    Instruction_t* fsave_wait = allocateNewInstruction(fileID, func);//9b
+    Instruction_t* fsave_esp_4 = allocateNewInstruction(fileID, func);//dd 74 24 04
+    Instruction_t* pushretaddress = allocateNewInstruction(fileID, func);
+    Instruction_t* frstor_esp_4 = allocateNewInstruction(fileID, func);//67 dd 64 24 04
+    
+    Instruction_t* test_eax_0 = allocateNewInstruction(fileID, func);
+    Instruction_t* test_eax_1 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* jz_eax_0 = allocateNewInstruction(fileID, func);
+    Instruction_t* jz_eax_1 = allocateNewInstruction(fileID, func);
+    
+    
+    Instruction_t* add_esp_0x70_label0 = allocateNewInstruction(fileID, func);
+    Instruction_t* add_esp_0x70_label1 = allocateNewInstruction(fileID, func);
+    Instruction_t* add_esp_0x70_label2 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* popf_label0 = allocateNewInstruction(fileID, func);
+    Instruction_t* popa_label0 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* popf_label1 = allocateNewInstruction(fileID, func);
+    Instruction_t* popa_label1 = allocateNewInstruction(fileID, func);
+    
+    Instruction_t* popf_label2 = allocateNewInstruction(fileID, func);
+    Instruction_t* popa_label2 = allocateNewInstruction(fileID, func);
+    Instruction_t* nop = allocateNewInstruction(fileID, func);
+    
+    
+    addPusha(pusha_i, pushf_i);//pusha
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pusha_i);
+	pusha_i->setFallthrough(pushf_i);
+    
+    addPushf(pushf_i, sub_esp_0x70);//pushf
+    
+    dataBits.resize(6);//sub esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xec;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    sub_esp_0x70->setFallthrough(fst_esp);
+    sub_esp_0x70->setDataBits(dataBits);
+    sub_esp_0x70->setComment(sub_esp_0x70->getDisassembly());
+	addInstruction(sub_esp_0x70, dataBits, fst_esp, NULL);
+    
+    dataBits.resize(3);//fst [esp]
+    dataBits[0] = 0xd9;
+    dataBits[1] = 0x14;
+    dataBits[2] = 0x24;
+    fst_esp->setFallthrough(fsave_esp_4);
+    fst_esp->setDataBits(dataBits);
+    fst_esp->setComment(fst_esp->getDisassembly());
+        addInstruction(fst_esp, dataBits, fsave_esp_4, NULL);
+    dataBits.resize(1);//fsave [esp+4]
+    dataBits[0] = 0x9b;
+    fsave_esp_4->setFallthrough(pushretaddress);
+    fsave_esp_4->setDataBits(dataBits);
+    fsave_esp_4->setComment(fsave_wait->getDisassembly());
+        addInstruction(fsave_wait, dataBits, fsave_esp_4, NULL);
+    dataBits.resize(4);
+    dataBits[0] = 0xdd;
+    dataBits[1] = 0x74;
+    dataBits[2] = 0x24;
+    dataBits[3] = 0x04;
+    fsave_esp_4->setFallthrough(pushretaddress);
+    fsave_esp_4->setDataBits(dataBits);
+    fsave_esp_4->setComment(fsave_esp_4->getDisassembly());
+        addInstruction(fsave_esp_4, dataBits, pushretaddress, NULL);
+    
+    virtual_offset_t AfterTheCheckerReturn = getAvailableAddress();
+	nop->getAddress()->SetVirtualOffset(AfterTheCheckerReturn);
+	nop->getAddress()->SetFileID(BaseObj_t::NOT_IN_DATABASE);
+    
+    dataBits.resize(5);//push return_address
+    dataBits[0] = 0x68;
+    virtual_offset_t *tmp;
+    tmp = (virtual_offset_t *) &dataBits[1];
+    *tmp = AfterTheCheckerReturn;
+    pushretaddress->setDataBits(dataBits);
+    pushretaddress->setComment(pushretaddress->getDisassembly());
+    pushretaddress->setFallthrough(nop);
+	
+    
+	dataBits.resize(1);//nop
+	dataBits[0] = 0x90;
+	nop->setDataBits(dataBits);
+	nop->setComment(nop->getDisassembly() + " -- with callback to floating number check") ;
+	nop->setFallthrough(frstor_esp_4);
+	nop->SetIndirectBranchTargetAddress(nop->getAddress());
+	if(len==32)
+        nop->SetCallback(string("FloatingRangeCheck32"));
+    else
+        nop->SetCallback(string("FloatingRangeCheck16"));
+    
+    dataBits.resize(4);//frstor [esp+4]
+    dataBits[0] = 0xdd;
+    dataBits[1] = 0x64;
+    dataBits[2] = 0x24;
+    dataBits[3] = 0x04;
+    frstor_esp_4->setDataBits(dataBits);
+    frstor_esp_4->setFallthrough(test_eax_0);
+    frstor_esp_4->setComment(frstor_esp_4->getDisassembly());
+    dataBits.resize(2);//test eax, eax
+    dataBits[0] = 0x85;
+    dataBits[1] = 0xC0;
+    test_eax_0->setDataBits(dataBits);
+    test_eax_0->setFallthrough(jz_eax_0);
+    addInstruction(test_eax_0, dataBits, jz_eax_0, NULL);
+    addJz(jz_eax_0, test_eax_1, add_esp_0x70_label0);
+    
+    
+    //label 0:
+    Instruction_t* jmpOriginalInst = allocateNewInstruction(fileID, func);
+    
+    dataBits.resize(6);//add esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xc4;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    add_esp_0x70_label0->setFallthrough(popf_label0);
+    add_esp_0x70_label0->setDataBits(dataBits);
+    add_esp_0x70_label0->setComment(add_esp_0x70_label0->getDisassembly());
+	addInstruction(add_esp_0x70_label0, dataBits, popf_label0, NULL);
+    
+    addPopf(popf_label0, popa_label0);
+    addPopa(popa_label0, jmpOriginalInst);
+    
+	
+	dataBits.resize(2);
+	dataBits[0] = 0xeb;
+	jmpOriginalInst->setComment("Jump to original Inst");
+	addInstruction(jmpOriginalInst,dataBits,NULL, originalInstrumentInstr);
+    
+    //label 1:
+    
+    dataBits.resize(5);//test eax, 1
+    dataBits[0] = 0xA9;
+    dataBits[1] = 0x01;
+    dataBits[2] = 0x00;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    test_eax_1->setDataBits(dataBits);
+    test_eax_1->setComment(test_eax_1->getDisassembly()) ;
+    test_eax_1->setFallthrough(jz_eax_1);
+    addInstruction(test_eax_1, dataBits, jz_eax_1, NULL);
+    addJz(jz_eax_1,  add_esp_0x70_label1, add_esp_0x70_label2);
+    
+    
+    dataBits.resize(6);//add esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xc4;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    add_esp_0x70_label1->setFallthrough(popf_label1);
+    add_esp_0x70_label1->setDataBits(dataBits);
+    add_esp_0x70_label1->setComment(add_esp_0x70_label1->getDisassembly());
+	addInstruction(add_esp_0x70_label1, dataBits, popf_label1, NULL);
+    addPopf(popf_label1, popa_label1);
+    
+    if(len==32){
+		Instruction_t* mov0x7FFFFFFF = allocateNewInstruction(fileID, func);
+		//Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label1, mov0x7FFFFFFF);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x7FFFFFFF->Assemble("mov "+ addExpr + ", 0x7FFFFFFF");
+        mov0x7FFFFFFF->setComment(mov0x7FFFFFFF->getDisassembly());
+		addInstruction(mov0x7FFFFFFF, mov0x7FFFFFFF->GetDataBits(), jmpOriginalInstNext, NULL);
+		popa_label1->setComment("just before " + mov0x7FFFFFFF->getDisassembly());
+		
+		//dataBits.resize(2);//fstp st(0)
+    	//dataBits[0] = 0xDD;
+    	//dataBits[1] = 0xD8;
+		//fstpST0->setDataBits(dataBits);
+		//fstpST0->setFallthrough(jmpOriginalInstNext);
+		//addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+        
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    else{
+    	Instruction_t* mov0x7FFF = allocateNewInstruction(fileID, func);
+    	//Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label1, mov0x7FFF);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x7FFF->Assemble("mov "+ addExpr + ", 0x7FFF");
+        mov0x7FFF->setComment(mov0x7FFF->getDisassembly());
+        
+		//mov0x7FFF->setFallthrough(fstpST0);
+		addInstruction(mov0x7FFF, mov0x7FFF->GetDataBits(), jmpOriginalInstNext, NULL);
+        
+		//dataBits.resize(2);//fstp st(0)
+    	//dataBits[0] = 0xDD;
+    	//dataBits[1] = 0xD8;
+        
+		//fstpST0->setDataBits(dataBits);
+		//fstpST0->setFallthrough(jmpOriginalInstNext);
+		//addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+		
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    
+    dataBits.resize(6);//add esp,0x70
+    dataBits[0] = 0x81;
+    dataBits[1] = 0xc4;
+    dataBits[2] = 0x70;
+    dataBits[3] = 0x00;
+    dataBits[4] = 0x00;
+    dataBits[5] = 0x00;
+    add_esp_0x70_label2->setFallthrough(popf_label2);
+    add_esp_0x70_label2->setDataBits(dataBits);
+    add_esp_0x70_label2->setComment(add_esp_0x70_label2->getDisassembly());
+    addInstruction(add_esp_0x70_label2, dataBits, popf_label2, NULL);
+    
+    addPopf(popf_label2, popa_label2);
+	if(len==32){
+		Instruction_t* mov0x80000000 = allocateNewInstruction(fileID, func);
+		//Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label2, mov0x80000000);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x80000000->Assemble("mov "+ addExpr + ", 0x80000001");
+        mov0x80000000->setComment(mov0x80000000->getDisassembly());
+       	//mov0x80000000->setFallthrough(fstpST0);
+		addInstruction(mov0x80000000, mov0x80000000->GetDataBits(), jmpOriginalInstNext, NULL);
+		
+		//dataBits.resize(2);//fstp st(0)
+    	//dataBits[0] = 0xDD;
+    	//dataBits[1] = 0xD8;
+        
+		//addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+        
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    else{
+    	Instruction_t* mov0x8000 = allocateNewInstruction(fileID, func);
+    	Instruction_t* fstpST0 =allocateNewInstruction(fileID, func);
+		Instruction_t* jmpOriginalInstNext = allocateNewInstruction(fileID, func);
+        
+        addPopa(popa_label2, mov0x8000);
+        string instrStr= originalInstrumentInstr->getDisassembly();
+        string addExpr = instrStr.substr(instrStr.find(" ")+1);
+        mov0x8000->Assemble("mov "+ addExpr + ", 0x8001");
+        mov0x8000->setComment(mov0x8000->getDisassembly());
+        
+		addInstruction(mov0x8000, mov0x8000->GetDataBits(), jmpOriginalInstNext, NULL);
+        
+		//dataBits.resize(2);//fstp st(0)
+    	//dataBits[0] = 0xDD;
+    	//dataBits[1] = 0xD8;
+        
+		//addInstruction(fstpST0, dataBits, jmpOriginalInstNext, NULL);
+		dataBits.resize(2);
+		dataBits[0] = 0xeb;
+		addInstruction(jmpOriginalInstNext,dataBits,NULL, originalInstrumentInstr->getFallthrough());
+    }
+    
+	m_numFP++;
+	return;
+}
+
+void IntegerTransform32::handleTruncation(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	if (p_annotation.getTruncationFromWidth() == 32)
+	{
+		if (p_annotation.getTruncationToWidth() == 8 || p_annotation.getTruncationToWidth() == 16)
+		{
+			addTruncationCheck(p_instruction, p_annotation, p_policy);
+		}
+		else
+		{
+			cerr << __func__ << ": TRUNCATION annotation not yet handled: " << p_annotation.toString() << "fromWidth: " << p_annotation.getTruncationFromWidth() << " toWidth: " << p_annotation.getTruncationToWidth() << endl;
+		}
+	}
+}
+
+//
+// before:       after:
+// <inst>        nop (with callback handler)
+//               <inst>
+//                     
+void IntegerTransform32::handleInfiniteLoop(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(getFileIR() && p_instruction);
+
+	logMessage(__func__, "handling infinite loop");
+
+    DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+    Function_t* func = p_instruction->GetFunction();
+
+	AddressID_t *originalAddress = p_instruction->getAddress();
+	Instruction_t* nop_i = allocateNewInstruction(fileID, func);
+
+	addNop(nop_i, p_instruction);
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, nop_i);
+
+	addCallbackHandler(string(INFINITE_LOOP_DETECTOR), originalInstrumentInstr, nop_i, nop_i->getFallthrough(), p_policy, originalAddress);
+}
+
+//
+//      <instruction to instrument>
+//      jno <originalFallthroughInstruction> 
+//      pusha
+//      pushf
+//      push_arg <address original instruction>
+//      push L1
+//      ... setup detector ...
+//  L1: pop_arg
+//      popf
+//      popa
+//
+// 20111024 Current policy:
+//            imul, mul -- always check using jno
+//            add, sub  -- use signedness information annotation to emit either jno, jnc
+//
+// p_addressOriginalInstruction is set when we call method from lea instrumentation
+void IntegerTransform32::addOverflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(getFileIR() && p_instruction && p_instruction->getFallthrough());
+	
+	RegisterName targetReg = getTargetRegister(p_instruction);
+	if (targetReg == rn_UNKNOWN) 
+	{
+		logMessage(__func__, "OVERFLOW UNKNOWN SIGN: unknown register -- skip instrumentation");
+		if (p_annotation.isUnderflow())
+			m_numUnderflowsSkipped++;
+		else
+			m_numOverflowsSkipped++;
+		return;
+	}
+
+cerr << __func__ <<  ": instr: " << p_instruction->getDisassembly() << " address: " << std::hex << p_instruction->getAddress() << " annotation: " << p_annotation.toString() << " policy: " << p_policy << endl;
+
+	string detector(INTEGER_OVERFLOW_DETECTOR);
+	string dataBits;
+
+	// old style of setting up these params
+	// update to cleaner style
+	Function_t* origFunction = p_instruction->GetFunction();
+	AddressID_t *jncond_a =new AddressID_t;
+	jncond_a->SetFileID(p_instruction->getAddress()->getFileID());
+	Instruction_t* jncond_i = new Instruction_t;
+	jncond_i->SetFunction(origFunction);
+	jncond_i->SetAddress(jncond_a);
+
+	// set fallthrough for the original instruction
+	Instruction_t* nextOrig_i = p_instruction->getFallthrough();
+	p_instruction->setFallthrough(jncond_i); 
+
+	// jncond 
+	dataBits.resize(2);
+	if (isMultiplyInstruction(p_instruction))
+	{
+		dataBits[0] = 0x71; // jno
+		dataBits[1] = 0x00; // value doesn't matter, we will fill it in later
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(MUL_OVERFLOW_DETECTOR_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(MUL_OVERFLOW_DETECTOR_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(MUL_OVERFLOW_DETECTOR_8);
+		cerr << "integertransform: MUL OVERFLOW: " << detector << endl;
+	}
+	else if (p_annotation.isUnsigned())
+	{
+		dataBits[0] = 0x73; // jnc
+		dataBits[1] = 0x00; // value doesn't matter, we will fill it in later
+
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_8);
+		cerr << "integertransform: UNSIGNED OVERFLOW: " << detector << endl;
+	}
+	else 
+	{
+		dataBits[0] = 0x71; // jno
+		dataBits[1] = 0x00; // value doesn't matter, we will fill it in later
+
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_SIGNED_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_SIGNED_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_SIGNED_8);
+		cerr << "integertransform: SIGNED OVERFLOW: " << detector << endl;
+	}
+
+	jncond_i->setDataBits(dataBits);
+	jncond_i->setComment(jncond_i->getDisassembly());
+	jncond_i->setTarget(nextOrig_i); 
+
+	p_instruction->setFallthrough(jncond_i); 
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		// implement saturating arithmetic, e.g.:
+		// mov <reg>, value
+		Instruction_t* saturate_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+
+		if (p_annotation.flowsIntoCriticalSink() && p_annotation.getBitWidth() == 32)
+		{
+			logMessage(__func__, "OVERFLOW UNSIGNED 32: CRITICAL SINK: saturate by masking");
+
+			DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+			Function_t* func = p_instruction->GetFunction();
+			Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+			Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+			addCallbackHandler(detector, p_instruction, jncond_i, pushf_i, p_policy);
+			addPushf(pushf_i, saturate_i);
+			addAndRegister32Mask(saturate_i, targetReg, 0x00FFFFFF, popf_i);
+			addPopf(popf_i, nextOrig_i);
+		}
+		else
+		{
+			addCallbackHandler(detector, p_instruction, jncond_i, saturate_i, p_policy);
+			addMaxSaturation(saturate_i, targetReg, p_annotation, nextOrig_i);
+		}
+	}
+	else
+	{
+		addCallbackHandler(detector, p_instruction, jncond_i, nextOrig_i, p_policy);
+	}
+
+	getFileIR()->getAddresses().insert(jncond_a);
+	getFileIR()->GetInstructions().insert(jncond_i);
+
+	if (p_annotation.isUnderflow())
+		m_numUnderflows++;
+	else
+		m_numOverflows++;
+}
+
+//
+//      <instruction to instrument>
+//      jno <originalFallthroughInstruction> 
+//      pusha
+//      pushf
+//      push_arg <address original instruction>
+//      push L1
+//      ... setup detector ...
+//  L1: pop_arg
+//      popf
+//      popa
+//
+// 20111024 Current policy:
+//            add, sub  -- use signedness information annotation to emit either jno, jnc
+//
+void IntegerTransform32::addUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(getFileIR() && p_instruction);
+
+	RegisterName targetReg = getTargetRegister(p_instruction);
+	if (targetReg == rn_UNKNOWN)
+	{
+		cerr << "IntegerTransform32::addUnderflowCheck(): instr: " << p_instruction->getDisassembly() << " address: " << p_instruction->getAddress() << " annotation: " << p_annotation.toString() << "-- SKIP b/c no target registers" << endl;
+		m_numUnderflowsSkipped++;
+		return;
+	}
+	
+	cerr << "IntegerTransform32::addUnderflowCheck(): instr: " << p_instruction->getDisassembly() << " address: " << p_instruction->getAddress() << " annotation: " << p_annotation.toString() << endl;
+
+	string detector(INTEGER_OVERFLOW_DETECTOR);
+	string dataBits;
+
+	// old style of setting up these params
+	// update to cleaner style
+	Function_t* origFunction = p_instruction->GetFunction();
+	AddressID_t *jncond_a =new AddressID_t;
+	jncond_a->SetFileID(p_instruction->getAddress()->getFileID());
+	Instruction_t* jncond_i = new Instruction_t;
+	jncond_i->SetFunction(origFunction);
+	jncond_i->SetAddress(jncond_a);
+
+	// set fallthrough for the original instruction
+	Instruction_t* nextOrig_i = p_instruction->getFallthrough();
+	p_instruction->setFallthrough(jncond_i); 
+
+	// jncond 
+	dataBits.resize(2);
+	if (p_annotation.isUnsigned())
+	{
+		dataBits[0] = 0x73; // jnc
+		dataBits[1] = 0x00; // value doesn't matter, we will fill it in later
+
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(UNDERFLOW_DETECTOR_UNSIGNED_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(UNDERFLOW_DETECTOR_UNSIGNED_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(UNDERFLOW_DETECTOR_UNSIGNED_8);
+		cerr << "integertransform: UNSIGNED OVERFLOW: " << detector << endl;
+	}
+	else if (p_annotation.isSigned())
+	{
+		dataBits[0] = 0x71; // jno
+		dataBits[1] = 0x00; // value doesn't matter, we will fill it in later
+
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(UNDERFLOW_DETECTOR_SIGNED_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(UNDERFLOW_DETECTOR_SIGNED_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(UNDERFLOW_DETECTOR_SIGNED_8);
+
+		cerr << "integertransform: SIGNED UNDERFLOW: " << detector << endl;
+	}
+	else
+	{
+		dataBits[0] = 0x71; // jno
+		dataBits[1] = 0x00; // value doesn't matter, we will fill it in later
+
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(UNDERFLOW_DETECTOR_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(UNDERFLOW_DETECTOR_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(UNDERFLOW_DETECTOR_8);
+		cerr << "integertransform: UNDERFLOW UNKONWN: assume signed for now: " << detector << endl;
+	}
+
+	jncond_i->setDataBits(dataBits);
+	jncond_i->setComment(jncond_i->getDisassembly());
+	jncond_i->setTarget(nextOrig_i); 
+
+	p_instruction->setFallthrough(jncond_i); 
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		// implement saturating arithmetic, e.g.:
+		// mov <reg>, value
+		Instruction_t* saturate_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+
+		addCallbackHandler(detector, p_instruction, jncond_i, saturate_i, p_policy);
+		addMinSaturation(saturate_i, targetReg, p_annotation, nextOrig_i);
+	}
+	else
+	{
+		addCallbackHandler(detector, p_instruction, jncond_i, nextOrig_i, p_policy);
+	}
+
+	getFileIR()->getAddresses().insert(jncond_a);
+	getFileIR()->GetInstructions().insert(jncond_i);
+
+	m_numUnderflows++;
+}
+
+
+//
+// STARS has extensive discussion of the logic behind truncation and
+//  signedness annotations in module SMPInstr.cpp, method EmitIntegerErrorAnnotation().
+//  The possible combinations are categorized in terms of the instrumentation
+//  needed at run time:
+//  CHECK TRUNCATION UNSIGNED : discarded bits must be all zeroes.
+//  CHECK TRUNCATION SIGNED: discarded bits must be sign-extension of stored bits.
+//  CHECK TRUNCATION UNKNOWNSIGN: discarded bits must be all zeroes, OR must
+//   be the sign-extension of the stored bits.
+// All truncation annotations are emitted on stores (mov opcodes in x86).
+//  Other possibilities might be handled in the future.
+//
+void IntegerTransform32::addTruncationCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(getFileIR() && p_instruction);
+	assert(p_annotation.getTruncationFromWidth() == 32 && p_annotation.getTruncationToWidth() == 8 || p_annotation.getTruncationToWidth() == 16);
+
+	cerr << __func__ << ": instr: " << p_instruction->getDisassembly() << " address: " << p_instruction->getAddress() << " annotation: " << p_annotation.toString() << " policy: " << p_policy << endl;
+
+	string detector; 
+
+	// Complicated case:
+	// 80484ed 3 INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+	//  example: for unknownsign truncation - 8 bit on AL
+	//          it's ok if 24 upper bits are sign-extension or all 0's
+	//          Re-phrased: upper 24 are 0s, upper 25 are 0s, upper 25 are 1s
+	//           are all OK in the UNKNOWNSIGN case
+	//          Note that upper 24 are 0's means no need to check for the
+	//           case where the upper 25 are 0's; already OK.
+	//
+	//             <save flags>
+	//             test eax, 0xFFFFFF00   ; (for 8 bit) 
+	//             jz <continue>          ; upper 24 bits are 0's 
+	//
+	//             cmp eax, 0xFFFFFF80    ;(for 8 bit) 
+	//             jae continue           ; upper 25 bits are 1's
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   saturating-arithmetic  ; optional
+	//
+	// continue:   <restore flags>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	//
+
+	// Unsigned case:
+	// 80484ed 3 INSTR CHECK TRUNCATION UNSIGNED 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+	//  example: for unsigned truncation - 8 bit on AL
+	//          it's ok if 24 upper bits are all 0's
+	//
+	//             <save flags>
+	//             test eax, 0xFFFFFF00   ; (for 8 bit) 
+	//             jz <continue>          ; upper 24 bits are 0's 
+	//
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   saturating-arithmetic  ; optional
+	//
+	// continue:   <restore flags>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	//
+
+	DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+	AddressID_t *saveAddress = p_instruction->getAddress();
+
+	Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* test_i = allocateNewInstruction(fileID, func);
+	Instruction_t* jz_i = allocateNewInstruction(fileID, func);
+	Instruction_t* saturate_i = NULL;
+	Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC) {
+		saturate_i = allocateNewInstruction(fileID, func);
+		addMaxSaturation(saturate_i, p_annotation.getRegister(), p_annotation, popf_i);
+	}
+
+	addPushf(pushf_i, test_i);
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, pushf_i);
+	pushf_i->setFallthrough(test_i); 
+	pushf_i->setComment("-- in truncation");
+	originalInstrumentInstr->setComment("-- in truncation (was original)");
+
+	unsigned mask = 0;
+	unsigned mask2 = 0;
+	if (p_annotation.getTruncationToWidth() == 16) {
+		mask = 0xFFFF0000;
+		mask2 = 0xFFFF8000;
+		if(p_annotation.flowsIntoCriticalSink()){
+			cerr <<"find flowsIntoCriticalSink in addTruncationCheck" <<endl;
+			detector = "forceSoupToExit";
+		}
+		else if (p_annotation.isUnsigned())
+			detector = string(TRUNCATION_DETECTOR_UNSIGNED_32_16);
+		else if (p_annotation.isSigned())
+			detector = string(TRUNCATION_DETECTOR_SIGNED_32_16);
+		else
+			detector = string(TRUNCATION_DETECTOR_32_16);
+	}
+	else if (p_annotation.getTruncationToWidth() == 8) {
+		mask = 0xFFFFFF00;
+		mask2 = 0xFFFFFF80;
+		if(p_annotation.flowsIntoCriticalSink()){
+			cerr <<"find flowsIntoCriticalSink in addTruncationCheck" <<endl;
+			detector = "forceSoupToExit";
+		}
+		else if (p_annotation.isUnsigned())
+			detector = string(TRUNCATION_DETECTOR_UNSIGNED_32_8);
+		else if (p_annotation.isSigned())
+			detector = string(TRUNCATION_DETECTOR_SIGNED_32_8);
+		else
+			detector = string(TRUNCATION_DETECTOR_32_8);
+	}
+         
+	if (p_annotation.isUnsigned()) {
+		addTestRegisterMask(test_i, p_annotation.getRegister(), mask, jz_i);
+		Instruction_t* nop_i = allocateNewInstruction(fileID, func);
+		addJz(jz_i, nop_i, popf_i); // target = popf_i, fall-through = nop_i
+
+		if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC) {
+			addNop(nop_i, saturate_i);
+			nop_i->setComment("UNSIGNED TRUNC: fallthrough: saturating arithmetic instruction");
+			addCallbackHandler(detector, originalInstrumentInstr, nop_i, saturate_i, p_policy, saveAddress);
+		}
+		else {
+			addNop(nop_i, popf_i);
+			nop_i->setComment(string("UNSIGNED TRUNC: fallthrough: popf"));
+			addCallbackHandler(detector, originalInstrumentInstr, nop_i, popf_i, p_policy, saveAddress);
+		}
+	}
+	else {
+		// Signed and unknown signed cases are almost identical:
+		// 80484ed 3 INSTR CHECK TRUNCATION SIGNED 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+		// 80484ed 3 INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+		//  example: for signed truncation - 8 bit on AL
+		//          it's ok if 25 upper bits are all 1's or all 0's
+		//  example: for unknownsign truncation - 8 bit on AL
+		//          it's ok if 25 upper bits are all 1's or 24 upper bits all 0's
+		//
+		//             <save flags>
+		//             test eax, 0xFFFFFF80   ; (for 8 bit) 0xFFFFFF00 for UNKNOWN
+		//             jz <continue>          ; upper 25 bits are 0's 
+		//
+		//             cmp eax, 0xFFFFFF80    ;(for 8 bit) 
+		//             jae continue           ; upper 25 bits are 1's
+		//             (invoke truncation handler) 
+		//             nop ; truncation handler callback here
+		//      SAT:   saturating-arithmetic  ; optional
+		//
+		// continue:   <restore flags>
+		//             mov [ebp+var_4], al    ; <originalInstruction>
+		//
+
+		if (p_annotation.isSigned()) {
+			addTestRegisterMask(test_i, p_annotation.getRegister(), mask2, jz_i);
+		}
+		else { // must be UNKNOWNSIGN
+			addTestRegisterMask(test_i, p_annotation.getRegister(), mask, jz_i);
+		}
+		Instruction_t* nop_i = allocateNewInstruction(fileID, func);
+		Instruction_t* s_cmp_i = allocateNewInstruction(fileID, func);
+		Instruction_t* s_jae_i = allocateNewInstruction(fileID, func);
+
+		addJz(jz_i, s_cmp_i, popf_i); // target = popf_i, fall-through = s_cmp_i
+		jz_i->setComment(string("jz - SIGNED or UNKNOWNSIGN TRUNC"));
+		addCmpRegisterMask(s_cmp_i, p_annotation.getRegister(), mask2, s_jae_i);
+		addJae(s_jae_i, nop_i, popf_i); // target = popf_i, fall-through = nop_i
+		s_jae_i->setComment(string("jae - SIGNED or UNKNOWNSIGN TRUNC"));
+
+		if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC) {
+			addNop(nop_i, saturate_i);
+			nop_i->setComment("SIGNED or UNKNOWNSIGN TRUNC: fallthrough: saturating arithmetic instruction");
+			addCallbackHandler(detector, originalInstrumentInstr, nop_i, saturate_i, p_policy, saveAddress);
+		}
+		else {
+			addNop(nop_i, popf_i);
+			nop_i->setComment(string("SIGNED or UNKNOWNSIGN TRUNC: fallthrough: popf"));
+			addCallbackHandler(detector, originalInstrumentInstr, nop_i, popf_i, p_policy, saveAddress);
+		}
+	} // end of SIGNED and UNKNOWNSIGN case
+	addPopf(popf_i, originalInstrumentInstr); // common to all cases
+
+	m_numTruncations++;
+	//    cerr << "addTruncationCheck(): --- END ---" << endl;
+}
+
+void IntegerTransform32::addSaturation(Instruction_t *p_instruction, RegisterName p_reg, unsigned p_value, const MEDS_InstructionCheckAnnotation& p_annotation, Instruction_t *p_fallthrough)
+{
+	assert(getFileIR() && p_instruction);
+
+	p_instruction->setFallthrough(p_fallthrough);
+
+	addMovRegisterUnsignedConstant(p_instruction, p_reg, p_value, p_fallthrough);
+}
+
+void IntegerTransform32::addZeroSaturation(Instruction_t *p_instruction, RegisterName p_reg, Instruction_t *p_fallthrough)
+{
+	assert(getFileIR() && p_instruction);
+
+	p_instruction->setFallthrough(p_fallthrough);
+
+	addMovRegisterUnsignedConstant(p_instruction, p_reg, 0, p_fallthrough);
+}
+
+//
+//      <instruction to instrument>
+//      jno <originalFallthroughInstruction> 
+//      jnc <originalFallthroughInstruction> 
+//      nop [attach callback handler]
+//      saturate target register (if policy dictates)
+//      <originalFallthroughInstruction>
+//
+void IntegerTransform32::addOverflowCheckUnknownSign(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(getFileIR() && p_instruction && p_instruction->getFallthrough());
+
+	RegisterName targetReg = getTargetRegister(p_instruction);
+	if (targetReg == rn_UNKNOWN)
+	{
+		cerr << "integertransform: OVERFLOW UNKNOWN SIGN: unknown register -- skip instrumentation" << endl;
+		m_numOverflowsSkipped++;
+		return;
+	}
+
+cerr << __func__ << ": instr: " << p_instruction->getDisassembly() << " address: " << std::hex << p_instruction->getAddress() << " annotation: " << p_annotation.toString() << " policy: " << p_policy << endl;
+	
+	// set detector/handler
+	string detector(OVERFLOW_UNKNOWN_SIGN_DETECTOR);
+	if (!isMultiplyInstruction(p_instruction))
+	{
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_8);
+	}
+
+	// for now assume we're dealing with add/sub 32 bit
+	DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->GetFunction();
+
+	Instruction_t* jno_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+	Instruction_t* jnc_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+	Instruction_t* nop_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+
+	// save fallthrough from original instruction
+	Instruction_t* nextOrig_i = p_instruction->getFallthrough();
+
+	// instrument for both jno and jnc
+	// redundant for imul, but that's ok, optimize later
+	p_instruction->setFallthrough(jno_i); 
+	addJno(jno_i, jnc_i, nextOrig_i);
+	addJnc(jnc_i, nop_i, nextOrig_i);
+	addNop(nop_i, nextOrig_i);
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC) 
+	{
+		Instruction_t* saturate_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+		addCallbackHandler(detector, p_instruction, nop_i, saturate_i, p_policy);
+		addMaxSaturation(saturate_i, targetReg, p_annotation, nextOrig_i);
+	}
+	else 
+	{
+		addCallbackHandler(detector, p_instruction, nop_i, nextOrig_i, p_policy);
+	}
+
+	m_numOverflows++;
+}
+
+//
+//      <instruction to instrument>
+//      jno|jnc <originalFallthroughInstruction> 
+//      jnc <originalFallthroughInstruction> [UNKNOWNSIGN]
+//      pusha
+//      pushf
+//      push_arg <address original instruction>
+//      push L1
+//      ... setup detector ...
+//  L1: pop_arg
+//      popf
+//      popa
+//
+// 20111024 Current policy:
+//            imul, mul -- always check using jno
+//            add, sub  -- use signedness information annotation to emit either jno, jnc
+//
+// p_addressOriginalInstruction is set when we call method from lea instrumentation
+void IntegerTransform32::addOverflowCheckForLea(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy, AddressID_t *p_addressOriginalInstruction)
+{
+	assert(getFileIR() && p_instruction && p_instruction->getFallthrough());
+	
+cerr << __func__ << ": comment: " << p_instruction->GetComment() << " annotation: " << p_annotation.toString() << " policy: " << p_policy << endl;
+
+	Instruction_t* jnc_i = NULL;
+	string detector(INTEGER_OVERFLOW_DETECTOR);
+
+	// this will be either jno or jnc
+	Instruction_t* jncond_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+
+	// set fallthrough for the original instruction
+	Instruction_t* nextOrig_i = p_instruction->getFallthrough();
+	p_instruction->setFallthrough(jncond_i); 
+
+	// jncond 
+	int isMultiply = isMultiplyInstruction(p_instruction);
+	if (isMultiply)
+	{
+		// fallthrough will be set by the callback handler
+		addJno(jncond_i, NULL, nextOrig_i);
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(MUL_OVERFLOW_DETECTOR_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(MUL_OVERFLOW_DETECTOR_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(MUL_OVERFLOW_DETECTOR_8);
+	}
+	else if (p_annotation.isSigned())
+	{
+		// fallthrough will be set by the callback handler
+		addJno(jncond_i, NULL, nextOrig_i);
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_8);
+	}
+	else if (p_annotation.isUnsigned())
+	{
+		// fallthrough will be set by the callback handler
+		addJnc(jncond_i, NULL, nextOrig_i);
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_8);
+	}
+	else
+	{
+		if (p_annotation.getBitWidth() == 32)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_32);
+		else if (p_annotation.getBitWidth() == 16)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_16);
+		else if (p_annotation.getBitWidth() == 8)
+			detector = string(ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_8);
+
+		jnc_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+
+		addJno(jncond_i, jnc_i, nextOrig_i);
+		addJnc(jnc_i, NULL, nextOrig_i); // fallthrough will be set by the callback handler
+	}
+
+	logMessage(__func__, "detector: " + detector);
+
+	if (jnc_i) // unknown add/sub
+	{
+		logMessage(__func__, "add callback handler for unknown add/sub");
+		addCallbackHandler(detector, p_instruction, jnc_i, nextOrig_i, p_policy, p_addressOriginalInstruction);
+	}
+	else
+	{
+		// mul, or signed/unsigned add/sub
+		logMessage(__func__, "add callback handler for mul, or signed/unsigned add/sub");
+		addCallbackHandler(detector, p_instruction, jncond_i, nextOrig_i, p_policy, p_addressOriginalInstruction);
+	}
+}
+
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform32.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform32.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..4617ecfdfb3bd2195a667e5a13ed0f8ab503e43b
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform32.hpp
@@ -0,0 +1,118 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef _LIBTRANSFORM_INTEGERTRANSFORM32_H_
+#define _LIBTRANSFORM_INTEGERTRANSFORM32_H_
+
+#include "integertransform.hpp"
+
+namespace libTransform
+{
+
+using namespace std;
+using namespace libIRDB;
+
+class IntegerTransform32 : public IntegerTransform
+{
+	public:
+		IntegerTransform32(VariantID_t *, FileIR_t*, 
+			MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, 
+				set<VirtualOffset> *p_warnings);
+
+		virtual int execute();
+		virtual int executePointerInstrumentation() { assert(0); } // not yet implemented
+
+	private:
+		void handleOverflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleSignedness(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleTruncation(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleFISTTruncation(Instruction_t *p_instruction);
+
+		void addFistpTruncationCheck(Instruction_t *p_instruction, int len);
+		void addFistTruncationCheck(Instruction_t *p_instruction, int len);
+
+		void handleInfiniteLoop(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		void addSignednessCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void addTruncationCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		void addOverflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void addOverflowCheckForLea(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy, AddressID_t *p_original);
+		void addOverflowCheckUnknownSign(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		void addUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		void addOverflowCheckNoFlag(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void addOverflowCheckNoFlag_RegPlusReg(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName&, const RegisterName&, const RegisterName&, int p_policy);
+		void addOverflowCheckNoFlag_RegPlusConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName&, int p_constantValue, const RegisterName&, int p_policy);
+		void addOverflowCheckNoFlag_RegTimesConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName&, int p_constantValue, const RegisterName&, int p_policy);
+
+		void addSaturation(Instruction_t *p_instruction, RegisterName p_reg, unsigned p_value, const MEDS_InstructionCheckAnnotation& p_annotation, Instruction_t *p_fallthrough);
+		void addZeroSaturation(Instruction_t *p_instruction, RegisterName p_reg, Instruction_t *p_fallthrough);
+
+};
+
+// make sure these match the function names in $STRATA/src/posix/x86_linux/detector_number_handling/overflow_detector.c
+
+#define	INTEGER_OVERFLOW_DETECTOR            "integer_overflow_detector"
+
+#define	ADDSUB_OVERFLOW_DETECTOR_SIGNED_32   "addsub_overflow_detector_signed_32"
+#define	ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_32 "addsub_overflow_detector_unsigned_32"
+#define	ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_32  "addsub_overflow_detector_unknown_32"
+
+#define	ADDSUB_OVERFLOW_DETECTOR_SIGNED_16   "addsub_overflow_detector_signed_16"
+#define	ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_16 "addsub_overflow_detector_unsigned_16"
+#define	ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_16  "addsub_overflow_detector_unknown_16"
+
+#define	ADDSUB_OVERFLOW_DETECTOR_SIGNED_8    "addsub_overflow_detector_signed_8"
+#define	ADDSUB_OVERFLOW_DETECTOR_UNSIGNED_8  "addsub_overflow_detector_unsigned_8"
+#define	ADDSUB_OVERFLOW_DETECTOR_UNKNOWN_8   "addsub_overflow_detector_unknown_8"
+
+#define	MUL_OVERFLOW_DETECTOR_32             "mul_overflow_detector_32"
+#define	MUL_OVERFLOW_DETECTOR_16             "mul_overflow_detector_16"
+#define	MUL_OVERFLOW_DETECTOR_8              "mul_overflow_detector_8"
+#define	TRUNCATION_DETECTOR                  "truncation_detector"
+#define	TRUNCATION_DETECTOR_32_16            "truncation_detector_32_16"
+#define	TRUNCATION_DETECTOR_32_8             "truncation_detector_32_8"
+#define	TRUNCATION_DETECTOR_16_8             "truncation_detector_16_8"
+#define	TRUNCATION_DETECTOR_UNSIGNED_32_16   "truncation_detector_unsigned_32_16"
+#define	TRUNCATION_DETECTOR_UNSIGNED_32_8    "truncation_detector_unsigned_32_8"
+#define	TRUNCATION_DETECTOR_UNSIGNED_16_8    "truncation_detector_unsigned_32_8"
+#define	TRUNCATION_DETECTOR_SIGNED_32_16     "truncation_detector_signed_32_16"
+#define	TRUNCATION_DETECTOR_SIGNED_32_8      "truncation_detector_signed_32_8"
+#define	TRUNCATION_DETECTOR_SIGNED_16_8      "truncation_detector_signed_32_8"
+#define	SIGNEDNESS_DETECTOR_32               "signedness_detector_32"
+#define	SIGNEDNESS_DETECTOR_16               "signedness_detector_16"
+#define	SIGNEDNESS_DETECTOR_8                "signedness_detector_8"
+#define UNDERFLOW_DETECTOR_32                "underflow_detector_32"
+#define UNDERFLOW_DETECTOR_16                "underflow_detector_16"
+#define UNDERFLOW_DETECTOR_8                 "underflow_detector_8"
+#define UNDERFLOW_DETECTOR_UNSIGNED_32       "underflow_detector_unsigned_32"
+#define UNDERFLOW_DETECTOR_UNSIGNED_16       "underflow_detector_unsigned_16"
+#define UNDERFLOW_DETECTOR_UNSIGNED_8        "underflow_detector_unsigned_8"
+#define UNDERFLOW_DETECTOR_SIGNED_32         "underflow_detector_signed_32"
+#define UNDERFLOW_DETECTOR_SIGNED_16         "underflow_detector_signed_16"
+#define UNDERFLOW_DETECTOR_SIGNED_8          "underflow_detector_signed_8"
+#define INFINITE_LOOP_DETECTOR               "infinite_loop_detector"
+#define	OVERFLOW_UNKNOWN_SIGN_DETECTOR       "overflow_unknown_sign_detector"
+}
+
+#endif
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform64.cpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform64.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..06315471f9fce669110366d7a760a1de0fb4d58c
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform64.cpp
@@ -0,0 +1,1702 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <assert.h>
+#include <sstream>
+#include "leapattern.hpp"
+#include "integertransform64.hpp"
+#include "Rewrite_Utility.hpp"
+
+#define INSTRUMENT_LEA
+#define INSTRUMENT_OVERFLOW
+#define INSTRUMENT_UNDERFLOW
+#define INSTRUMENT_TRUNCATION
+#define INSTRUMENT_SIGNEDNESS
+
+using namespace libTransform;
+
+/**
+*     64 bit implementation status of the integer transform
+*     20140228 64-bit overflows on multiply, signed/unsigned add/sub
+*     20140422 callback handlers added
+*
+*      64-bit        signed     unsigned   unknown
+*      --------      ------     --------   -------
+*      add, sub       of          c         of,c
+*        mul          of          of         of
+*        lea         @todo      @todo       @todo
+*             
+*      32-bit        signed     unsigned   unknown
+*      --------      ------     --------   -------
+*      add, sub      @todo      @todo       @todo
+*        mul          of          of         of
+*        lea         @todo      @todo       @todo
+
+*     @todo:
+*           - test unknown
+*           - test warnings only mode
+*           - handle LEA instructions
+*
+**/
+
+IntegerTransform64::IntegerTransform64(VariantID_t *p_variantID, FileIR_t *p_fileIR, MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_benignFalsePositives) : IntegerTransform(p_variantID, p_fileIR, p_annotations, p_filteredFunctions, p_benignFalsePositives)
+{
+}
+
+// iterate through all functions
+// filter those functions that should be ignored
+//    iterate through all instructions in function
+//    if MEDS annotation says to instrument
+//       add instrumentation
+int IntegerTransform64::execute()
+{
+	if (isWarningsOnly())
+		logMessage(__func__, "warnings only mode");
+	if (isInstrumentIdioms())
+		logMessage(__func__, "override annotations -- instrument IDIOMS");
+
+	for(
+	  set<Function_t*>::const_iterator itf=getFileIR()->GetFunctions().begin();
+	  itf!=getFileIR()->GetFunctions().end();
+	  ++itf
+	  )
+	{
+		Function_t* func=*itf;
+
+		if (getFilteredFunctions()->find(func->GetName()) != getFilteredFunctions()->end())
+		{
+			logMessage(__func__, "filter out: " + func->GetName());
+			continue;
+		}
+
+		if (isBlacklisted(func))
+		{
+			logMessage(__func__, "blacklisted: " + func->GetName());
+			m_numBlacklisted++;
+			continue;
+		}
+
+		logMessage(__func__, "processing fn: " + func->GetName());
+
+		for(
+		  set<Instruction_t*>::const_iterator it=func->GetInstructions().begin();
+		  it!=func->GetInstructions().end();
+		  ++it)
+		{
+			Instruction_t* insn=*it;
+
+			if (insn && insn->getAddress())
+			{
+				int policy = POLICY_DEFAULT; 
+
+				if (isSaturatingArithmetic())
+				{
+					// saturating arithmetic is enabled
+					// only use if instruction is not a potential false positive
+					policy = POLICY_CONTINUE_SATURATING_ARITHMETIC;
+				}
+
+				// takes precedence over saturation if conflict
+				if (isWarningsOnly())
+				{
+					policy = POLICY_CONTINUE;
+				}
+
+				virtual_offset_t irdb_vo = insn->getAddress()->GetVirtualOffset();
+				if (irdb_vo == 0) continue;
+
+				VirtualOffset vo(irdb_vo);
+
+				if (getAnnotations()->count(vo) == 0)
+					continue;
+
+				std::pair<MEDS_Annotations_t::iterator,MEDS_Annotations_t::iterator> ret;
+				ret = getAnnotations()->equal_range(vo);
+				MEDS_InstructionCheckAnnotation annotation; 
+				MEDS_InstructionCheckAnnotation* p_annotation; 
+				for ( MEDS_Annotations_t::iterator it = ret.first; it != ret.second; ++it)
+				{
+					MEDS_AnnotationBase *base_type=(it->second);
+					p_annotation = dynamic_cast<MEDS_InstructionCheckAnnotation*>(base_type);
+					if( p_annotation == NULL)
+						continue;
+					annotation = *p_annotation;
+					if (!annotation.isValid()) 
+						continue;
+					else
+						break; // let's just handle one annotation for now and see how it goes
+				}
+
+				logMessage(__func__, annotation, "-- instruction: " + insn->getDisassembly());
+				m_numAnnotations++;
+
+				if (annotation.isIdiom() && !isInstrumentIdioms())
+				{
+					logMessage(__func__, "skip IDIOM");
+					m_numIdioms++;
+					continue;
+				}
+
+				if (!insn->getFallthrough())
+				{
+					logMessage(__func__, "Warning: no fall through for instruction -- skipping");
+					continue;
+				}
+
+				if (annotation.isOverflow())
+				{
+#ifdef INSTRUMENT_OVERFLOW
+					m_numTotalOverflows++;
+					handleOverflowCheck(insn, annotation, policy);
+#endif
+				}
+#ifdef INSTRUMENT_UNDERFLOW
+				else 
+				if (annotation.isUnderflow())
+				{
+					m_numTotalUnderflows++;
+					handleUnderflowCheck(insn, annotation, policy);
+				}
+#endif
+#ifdef INSTRUMENT_TRUNCATION
+				else if (annotation.isTruncation())
+				{
+					m_numTotalTruncations++;
+					handleTruncation(insn, annotation, policy);
+				}
+#endif
+#ifdef INSTRUMENT_SIGNEDNESS
+				else if (annotation.isSignedness())
+				{
+					m_numTotalSignedness++;
+					handleSignedness(insn, annotation, policy);
+				}
+#endif
+			}
+		} // end iterate over all instructions in a function
+	} // end iterate over all functions
+
+	return 0;
+}
+
+void IntegerTransform64::handleOverflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	bool result = false;
+
+	if (isMultiplyInstruction(p_instruction) || (p_annotation.isOverflow() && !p_annotation.isNoFlag()))
+	{
+		// handle signed/unsigned add/sub overflows (non lea)
+		result = addOverflowUnderflowCheck(p_instruction, p_annotation, p_policy);
+	}
+#ifdef INSTRUMENT_LEA
+	else 
+	if (p_annotation.isNoFlag())
+	{
+		// handle lea
+		if ((p_annotation.getBitWidth() == 64 || p_annotation.getBitWidth() == 32))
+		{
+			result = addOverflowCheckNoFlag(p_instruction, p_annotation, p_policy);
+		}
+	}
+#endif
+
+	if (result)
+	{
+		m_numOverflows++;
+	}
+	else
+	{
+		m_numOverflowsSkipped++;
+		logMessage(__func__, "OVERFLOW type not yet handled");
+	}
+}
+
+void IntegerTransform64::handleUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	bool success = false;
+
+	if (p_annotation.isUnderflow() && !p_annotation.isNoFlag())
+		success = addOverflowUnderflowCheck(p_instruction, p_annotation, p_policy);
+
+	if (success)
+	{
+		m_numUnderflows++;
+	}
+	else
+	{
+		m_numUnderflowsSkipped++;
+		logMessage(__func__, "UNDERFLOW type not yet handled");
+	}
+}
+
+void IntegerTransform64::handleTruncation(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	bool success = false;
+
+	if (!isMovInstruction(p_instruction))
+	{
+		logMessage(__func__, "We only instrument MOV instructions for TRUNCATION annotations");
+		return;
+	}
+
+	if (p_annotation.getTruncationFromWidth() == 64)
+	{
+		if (p_annotation.getTruncationToWidth() == 32 || p_annotation.getTruncationToWidth() == 16 || p_annotation.getTruncationToWidth() == 8)
+		{
+			success = addTruncationCheck64(p_instruction, p_annotation, p_policy);
+		}
+		else
+		{
+			logMessage(__func__, "Truncation type not yet handled (64)");
+		}
+	}
+	else if (p_annotation.getTruncationFromWidth() == 32)
+	{
+		if (p_annotation.getTruncationToWidth() == 16 || p_annotation.getTruncationToWidth() == 8)
+		{
+			success = addTruncationCheck32(p_instruction, p_annotation, p_policy);
+		}
+		else
+		{
+			logMessage(__func__, "Truncation type not yet handled (32)");
+		}
+	}
+
+	if (success)
+		m_numTruncations++;
+	else
+	{
+		m_numTruncationsSkipped++;
+		logMessage(__func__, "Truncation type not yet handled (2)");
+	}
+}
+
+void IntegerTransform64::handleSignedness(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	if (addSignednessCheck(p_instruction, p_annotation, p_policy))
+	{
+                m_numSignedness++;
+	}
+	else
+	{
+                logMessage(__func__, "SIGNEDNESS: error: skip instrumentation");
+                m_numSignednessSkipped++;
+	}
+}
+
+
+//
+// Saturation Policy
+//	            mul a, b                 ; <instruction to instrument>
+//              jno <OrigNext>           ; if no overflows, jump to original fallthrough instruction
+//              mov a, MIN/MAX           ; policy = min-saturate (underflow) / max-saturate (overflow)
+//              of64/uf64 handler        ; call the callback handler (handle diagnostics)
+// OrigNext:    <nextInstruction>        ; original fallthrugh
+//
+bool IntegerTransform64::addOverflowUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	char tmpbuf[1024];
+
+	assert(getFileIR() && p_instruction && p_instruction->getFallthrough());
+	RegisterName targetReg = getTargetRegister(p_instruction);
+	if (targetReg == rn_UNKNOWN)
+	{
+		logMessage(__func__, p_annotation, "unknown target register");
+		return false;
+	}
+	else if (!instrumentSP() && (targetReg == rn_RSP || targetReg == rn_ESP)) 
+	{
+		logMessage(__func__, "target register is esp/rsp -- skipping: ");
+		return false;
+	}
+	else if (!instrumentFP() && (targetReg == rn_RBP || targetReg == rn_EBP)) 
+	{
+		logMessage(__func__, "target register is ebp/rbp -- skipping: ");
+		return false;
+	}
+
+	Instruction_t* jncond_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+	Instruction_t* nop_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+	Instruction_t* policy_i;
+
+	Instruction_t* next_i = p_instruction->getFallthrough();
+	p_instruction->setFallthrough(jncond_i); 
+
+	setAssembly(nop_i, "nop");  
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		policy_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+	}
+	else
+	{
+		policy_i = nop_i;
+	}
+
+	if (p_annotation.isSigned() || isMultiplyInstruction(p_instruction))
+	{
+		addJno(jncond_i, policy_i, next_i); 
+	}
+	else if (p_annotation.isUnsigned())
+	{
+		addJnc(jncond_i, policy_i, next_i);
+	}
+	else
+	{ 	// unknown sign
+		Instruction_t* jnc_i = allocateNewInstruction(p_instruction->getAddress()->getFileID(), p_instruction->GetFunction());
+		addJno(jncond_i, jnc_i, next_i); 
+		addJnc(jnc_i, policy_i, next_i); 
+	}
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		// @todo:
+		//    saturating signed multiply overflow should take into account
+		//    the signs of the operand. If multiplying negative by positive #,
+		//    then we want to sature to MIN_SIGNED_INT
+		
+		if (p_annotation.isUnderflow())
+			addMinSaturation(policy_i, targetReg, p_annotation, nop_i); 
+		else
+			addMaxSaturation(policy_i, targetReg, p_annotation, nop_i);
+	}
+
+	std::string detector = p_annotation.isOverflow() ? OVERFLOW64_DETECTOR : UNDERFLOW64_DETECTOR;
+
+	Instruction_t* cb = addCallbackHandlerSequence(p_instruction, next_i, detector, p_policy);
+	nop_i->setFallthrough(cb);
+	cb->setComment("underflow callback/instrumentation");
+
+	return true;
+}
+
+bool IntegerTransform64::addOverflowCheckNoFlag(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	LEAPattern leaPattern(p_annotation);
+
+	if (!leaPattern.isValid())
+	{
+		logMessage(__func__, "invalid or unhandled lea pattern - skipping: ");
+		return false;
+	}
+
+	if (leaPattern.getRegister1() == rn_UNKNOWN)
+	{
+		logMessage(__func__, "destination register is unknown -- skipping: ");
+		return false;
+	}
+	else if(!instrumentSP() && (leaPattern.getRegister1() == rn_RSP || leaPattern.getRegister1() == rn_ESP))
+	{
+		logMessage(__func__, "destination register is r/esp -- skipping: ");
+		return false;
+	}
+	else if(!instrumentFP() && (leaPattern.getRegister1() == rn_RBP || leaPattern.getRegister1() == rn_EBP))
+	{
+		logMessage(__func__, "destination register is r/ebp -- skipping: ");
+		return false;
+	}
+
+	if (leaPattern.isRegisterPlusRegister() || leaPattern.isRegisterTimesRegister())
+	{
+		RegisterName reg1 = leaPattern.getRegister1();
+		RegisterName reg2 = leaPattern.getRegister2();
+		RegisterName target = getTargetRegister(p_instruction);
+
+		if (reg1 == rn_UNKNOWN || reg2 == rn_UNKNOWN || target == rn_UNKNOWN)
+		{
+			logMessage(__func__, "lea reg reg pattern: error retrieving register: reg1: " + Register::toString(reg1) + " reg2: " + Register::toString(reg2) + " target: " + Register::toString(target));
+			return false;
+		}
+		else if (!instrumentSP() && (reg2 == rn_RSP || reg2 == rn_ESP || reg1 == rn_RSP || reg1 == rn_ESP )) 
+		{
+			logMessage(__func__, "source or target register is esp/rsp -- skipping: ");
+			return false;
+		}
+		else if (!instrumentFP() && (reg2 == rn_RBP || reg2 == rn_EBP || reg1 == rn_RBP || reg1 == rn_EBP )) 
+		{
+			logMessage(__func__, "source or target register is ebp/rbp -- skipping: ");
+			return false;
+		}
+		else
+		{
+			if (leaPattern.isRegisterPlusRegister())
+				addOverflowCheckNoFlag_RegPlusReg(p_instruction, p_annotation, reg1, reg2, target, p_policy);
+			else if (leaPattern.isRegisterTimesRegister())
+				addOverflowCheckNoFlag_RegTimesReg(p_instruction, p_annotation, reg1, reg2, target, p_policy);
+		}
+		return true;
+	}
+	else if (leaPattern.isRegisterPlusConstant() || leaPattern.isRegisterTimesConstant())
+	{
+		RegisterName reg1 = leaPattern.getRegister1();
+		int k = leaPattern.getConstant();
+		RegisterName target = getTargetRegister(p_instruction);
+
+		if (reg1 == rn_UNKNOWN || target == rn_UNKNOWN)
+		{
+			logMessage(__func__, "lea reg const pattern: error retrieving register: reg1: " + Register::toString(reg1) + " target: " + Register::toString(target));
+			return false;
+		}
+		else if (!instrumentSP() && (target == rn_RSP || target == rn_ESP)) 
+		{
+			logMessage(__func__, "target register is esp/rsp -- skipping: ");
+			return false;
+		}
+		else if (!instrumentFP() && (target == rn_RBP || target == rn_EBP)) 
+		{
+			logMessage(__func__, "target register is ebp/rbp -- skipping: ");
+			return false;
+		}
+		else
+		{
+			if (leaPattern.isRegisterPlusConstant())
+				addOverflowCheckNoFlag_RegPlusConstant(p_instruction, p_annotation, reg1, k, target, p_policy);
+			else if (leaPattern.isRegisterTimesConstant())
+				addOverflowCheckNoFlag_RegTimesConstant(p_instruction, p_annotation, reg1, k, target, p_policy);
+		}
+		return true;
+	}
+	logMessage(__func__, "not yet handling lea -- placeholder");
+	return false;
+}
+
+//
+// p_orig          original instruction being instrumented
+// p_fallthrough   fallthrough once we're done with the callback handlers/detectors
+// p_detector      callback handler function to call
+// p_policy        instrumentation policy (e.g.: terminate, saturate, ...)
+// 
+// returns first instruction of callback handler sequence
+//
+Instruction_t* IntegerTransform64::addCallbackHandlerSequence(Instruction_t *p_orig, Instruction_t *p_fallthrough, std::string p_detector, int p_policy)
+{
+	char tmpbuf[1024];
+
+	Instruction_t* lea = addNewAssembly("lea rsp, [rsp-128]");  // red zone 
+	lea->setComment("callback: " + p_detector);
+
+    // must save flags as strata will perturb them
+    Instruction_t* saveFlags = addNewAssembly(lea, "pushf");
+
+	// pass in PC of instrumented instruction
+	// pass in p_policy 
+	sprintf(tmpbuf,"push 0x%08x", p_policy);  
+	Instruction_t* instr = addNewAssembly(saveFlags, tmpbuf);
+	sprintf(tmpbuf,"push 0x%08x", p_orig->getAddress()->GetVirtualOffset()); 
+	instr = addNewAssembly(instr, tmpbuf);
+
+	Instruction_t* call = allocateNewInstruction(p_orig->getAddress()->getFileID(), p_orig->GetFunction());
+	instr->setFallthrough(call);
+	setAssembly(call, "call 0"); 
+		
+	addCallbackHandler64(call, p_detector, 2); // 2 args for now
+
+	assert(call->getTarget());
+
+	instr = addNewAssembly(call, "lea rsp, [rsp+16]");  
+	instr = addNewAssembly(instr, "popf");  
+	instr = addNewAssembly(instr, "lea rsp, [rsp+128]");  
+	instr->setFallthrough(p_fallthrough);
+
+	return lea;
+}
+
+// Example annotation to handle
+// 804852e      3 INSTR CHECK OVERFLOW NOFLAGSIGNED 32 EDX+EAX ZZ lea     eax, [edx+eax] Reg1: EDX Reg2: EAX
+// Need to handle both 32-bit and 64-bit versions
+//
+// Original:
+//   lea r3, [r1+r2]
+//   <originalNext>
+//
+// Instrumentation:
+//   push r1                ;   save r1
+//   pushf                  ;   save flags
+//   add r1, r2             ;   r1 = r1 + r2
+//        <overflowcheck>   ;   check for overflow 
+//          (jno|jnc <restore>)   ; SIGNED|UNSIGNED
+//            fallthrough--><policy>
+//          (jno&jnc <restore>)   ; UNKNOWNSIGN check both flags  
+//            fallthrough--><policy>
+//
+// <restore>
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//
+// <orig>: lea r3, [r1+r2]        ; original instruction        
+//         <originalNext>         ; original next instruction
+//
+// <policy>                  
+//         () callback handler 
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//            fallthrough-->originalNext (if no saturation)
+//         saturateMax(r3)        ; optional saturation
+//            fallthrough-->originalNext
+//
+void IntegerTransform64::addOverflowCheckNoFlag_RegPlusReg(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const RegisterName& p_reg2, const RegisterName& p_reg3, int p_policy)
+{
+	assert(p_instruction && p_instruction->getFallthrough());
+
+	cerr << __func__ << ": r3 <-- r1+r2: r1: " << Register::toString(p_reg1) << " r2: " << Register::toString(p_reg2) << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+	Instruction_t *instr, *first, *saturation_policy;
+	Instruction_t *restore = addNewAssembly("popf");
+
+	saturation_policy = addNewAssembly("nop");
+	saturation_policy->setComment("lea overflow instrumentation(reg+reg): policy code sequence");
+
+	// Original code sequence:
+	//   lea r3, [r1+r2]
+	//   <originalNext>
+	//
+	// Instrumentation:
+	//   push r1                ;   save r1
+	//   pushf                  ;   save flags
+	//   add r1, r2             ;   r1 = r1 + r2
+	//        <overflowcheck>   ;   check for overflow 
+	//          (jno|jnc <restore>)   ; SIGNED|UNSIGNED
+	//            fallthrough--><policy>
+	//          (jno&jnc <restore>)   ; UNKNOWNSIGN check both flags  
+	//            fallthrough--><policy>
+	//
+//	first = addNewAssembly("push " + Register::toString(p_reg1)); 
+//	first->setComment("lea overflow instrumentation(reg+reg): start");
+//	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, first);
+
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, "lea rsp, [rsp-128]" , NULL);
+	p_instruction->setComment("lea overflow instrumentation(reg+reg): start");
+	instr = addNewAssembly(p_instruction, std::string("push ") + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "pushf");
+
+	instr = addNewAssembly(instr, "add " + Register::toString(p_reg1) + "," + Register::toString(p_reg2));
+	if (p_annotation.isSigned())
+	{
+		instr = addNewAssembly(instr, "jno 0x22");
+		instr->setFallthrough(saturation_policy);
+		instr->setTarget(restore);
+		instr->setComment("signed: lea: reg+reg");
+	}
+	else if (p_annotation.isUnsigned())
+	{
+		instr = addNewAssembly(instr, "jnc 0x22");
+		instr->setFallthrough(saturation_policy);
+		instr->setTarget(restore);
+	}
+	else
+	{
+		Instruction_t *instr2 = addNewAssembly(instr, "jno 0x22"); // this generates bogus assembly code, why?
+		instr2->setTarget(restore);
+		instr = addNewAssembly(instr2, "jnc 0x22");
+		instr->setFallthrough(saturation_policy);
+		instr->setTarget(restore);
+	}
+
+	// <policy>                  
+	//         nop                    ;
+	//         () callback handler    ;
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//            fallthrough-->originalNext (if no saturation)
+	//         saturateMax(r3)        ; optional saturation
+	//            fallthrough-->originalNext
+	//
+	// assume 64 bit for now
+	//
+	Instruction_t *popf = addNewAssembly("popf");
+	Instruction_t *callback = addCallbackHandlerSequence(p_instruction, popf, OVERFLOW64_DETECTOR, p_policy);
+	saturation_policy->setFallthrough(callback);
+	instr = addNewAssembly(popf, "pop " + Register::toString(p_reg1));
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		instr = addNewMaxSaturation(instr, p_reg3, p_annotation);
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(origFallthrough);
+	}
+	else
+	{
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(originalInstrumentInstr);
+	}
+
+	// <restore>
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//
+	// <orig>: lea r3, [r1+r2]        ; original instruction        
+	//         <originalNext>         ; original next instruction
+	//
+	restore->setComment("lea overflow instrumentation(reg+reg): restore");
+	instr = addNewAssembly(restore, "pop " + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+	instr->setFallthrough(originalInstrumentInstr);
+}
+
+// Example annotation to handle
+// 804852e      3 INSTR CHECK OVERFLOW NOFLAGSIGNED 32 EDX+EAX ZZ lea     eax, [edx+eax] Reg1: EDX Reg2: EAX
+// Need to handle both 32-bit and 64-bit versions
+//
+// Original:
+//   lea r3, [r1+r2]
+//   <originalNext>
+//
+// Instrumentation:
+//   push r1                ;   save r1
+//   pushf                  ;   save flags
+//   imul r1, r2             ;   r1 = r1 * r2
+//        <overflowcheck>   ;   check for overflow 
+//          (jno|jnc <restore>)   ; SIGNED|UNSIGNED
+//            fallthrough--><policy>
+//          (jno&jnc <restore>)   ; UNKNOWNSIGN check both flags  
+//            fallthrough--><policy>
+//
+// <restore>
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//
+// <orig>: lea r3, [r1+r2]        ; original instruction        
+//         <originalNext>         ; original next instruction
+//
+// <policy>                  
+//         () callback handler 
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//            fallthrough-->originalNext (if no saturation)
+//         saturateMax(r3)        ; optional saturation
+//            fallthrough-->originalNext
+//
+void IntegerTransform64::addOverflowCheckNoFlag_RegTimesReg(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const RegisterName& p_reg2, const RegisterName& p_reg3, int p_policy)
+{
+	assert(p_instruction && p_instruction->getFallthrough());
+
+	cerr << __func__ << ": r3 <-- r1*r2: r1: " << Register::toString(p_reg1) << " r2: " << Register::toString(p_reg2) << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+	Instruction_t *instr, *first, *saturation_policy;
+	Instruction_t *restore = addNewAssembly("popf");
+	saturation_policy = addNewAssembly("nop");
+	saturation_policy->setComment("lea overflow instrumentation(reg*reg): policy code sequence");
+
+
+	// Original code sequence:
+	//   lea r3, [r1*r2]
+	//   <originalNext>
+	//
+	// Instrumentation:
+	//   push r1                ;   save r1
+	//   pushf                  ;   save flags
+	//   imul r1, r2            ;   r1 = r1 * r2
+	//        <overflowcheck>   ;   check for overflow 
+	//        jno <restore>     ; 
+	//           fallthrough--><policy>
+	//
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, "lea rsp, [rsp-128]" , NULL);
+	p_instruction->setComment("lea overflow instrumentation(reg*reg): start");
+	instr = addNewAssembly(p_instruction, std::string("push ") + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "pushf");
+
+	instr = addNewAssembly(instr, "imul " + Register::toString(p_reg1) + "," + Register::toString(p_reg2));
+	instr = addNewAssembly(instr, "jno 0x22");
+	instr->setFallthrough(saturation_policy);
+	instr->setTarget(restore);
+
+	// <policy>                  
+	//         nop                    ;
+	//         () callback handler    ;
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//            fallthrough-->originalNext (if no saturation)
+	//         saturateMax(r3)        ; optional saturation
+	//            fallthrough-->originalNext
+	//
+	// assume 64 bit for now
+	//
+	Instruction_t *popf = addNewAssembly("popf");
+	Instruction_t *callback = addCallbackHandlerSequence(p_instruction, popf, OVERFLOW64_DETECTOR, p_policy);
+	saturation_policy->setFallthrough(callback);
+	instr = addNewAssembly(popf, "pop " + Register::toString(p_reg1));
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		instr = addNewMaxSaturation(instr, p_reg3, p_annotation);
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(origFallthrough);
+	}
+	else
+	{
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(originalInstrumentInstr);
+	}
+
+	// <restore>
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//
+	// <orig>: lea r3, [r1*r2]        ; original instruction        
+	//         <originalNext>         ; original next instruction
+	//
+	restore->setComment("lea overflow instrumentation(reg*reg): restore");
+	instr = addNewAssembly(restore, "pop " + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+	instr->setFallthrough(originalInstrumentInstr);
+}
+
+// Example annotation to handle
+// 804852e      3 INSTR CHECK OVERFLOW NOFLAGSIGNED 32 EDX+EAX ZZ lea     eax, [edx+k] Reg1: EDX Reg3: EAX
+// Need to handle both 32-bit and 64-bit versions
+//
+// Original:
+//   lea r3, [r1+k]
+//   <originalNext>
+//
+// Instrumentation:
+//   push r1                ;   save r1
+//   pushf                  ;   save flags
+//   add r1, k              ;   r1 = r1 + k
+//        <overflowcheck>   ;   check for overflow 
+//          (jno|jnc <restore>)   ; SIGNED|UNSIGNED
+//            fallthrough--><policy>
+//          (jno&jnc <restore>)   ; UNKNOWNSIGN check both flags  
+//            fallthrough--><policy>
+//
+// <restore>
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//
+// <orig>: lea r3, [r1+k]         ; original instruction        
+//         <originalNext>         ; original next instruction
+//
+// <policy>                  
+//         () callback handler 
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//            fallthrough-->originalNext (if no saturation)
+//         saturateMax(r3)        ; optional saturation
+//            fallthrough-->originalNext
+//
+void IntegerTransform64::addOverflowCheckNoFlag_RegPlusConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const int p_constant, const RegisterName& p_reg3, int p_policy)
+{
+	assert(p_instruction && p_instruction->getFallthrough());
+
+	if (p_annotation.isUnsigned() && (p_constant < 0)) {
+	  logMessage(__func__, "lea reg+neg constant pattern: skip this annotation type (prone to false positives)");
+	  m_numOverflowsSkipped++;
+	  return;
+	}
+
+	cerr << __func__ << ": r3 <-- r1+k: r1: " << Register::toString(p_reg1) << " k: " << p_constant << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+	Instruction_t *instr, *first, *saturation_policy;
+	Instruction_t *restore = addNewAssembly("popf");
+	saturation_policy = addNewAssembly("nop");
+	saturation_policy->setComment("lea overflow instrumentation(reg+k): policy code sequence");
+
+	// Original code sequence:
+	//   lea r3, [r1+k]
+	//   <originalNext>
+	//
+	// Instrumentation:
+	//   push r1                ;   save r1
+	//   pushf                  ;   save flags
+	//   add r1, k              ;   r1 = r1 + k
+	// (or sub r1,-k            ;   r1 = r1 - (-k) for k < 0)
+	//        <overflowcheck>   ;   check for overflow 
+	//          (jno|jnc <restore>)   ; SIGNED|UNSIGNED
+	//            fallthrough--><policy>
+	//          (jno&jnc <restore>)   ; UNKNOWNSIGN check both flags  
+	//            fallthrough--><policy>
+	//
+/*
+	first = addNewAssembly("push " + Register::toString(p_reg1)); 
+	first->setComment("lea overflow instrumentation(reg+k): start");
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, first);
+	instr = addNewAssembly(first, "pushf");
+	*/
+
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, "lea rsp, [rsp-128]" , NULL);
+	p_instruction->setComment("lea overflow instrumentation(reg+k): start");
+	instr = addNewAssembly(p_instruction, std::string("push ") + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "pushf");
+//-------------------
+	// make sure we set the fallthrough post careful insertion
+//	first->setFallthrough(instr);
+
+	std::ostringstream s;
+	if (p_constant >= 0) {
+	  s << "add " << Register::toString(p_reg1) << "," << p_constant;
+	}
+	else {
+	  // NOTE: We are short-circuiting this case currently; see top of
+	  //  this function. Should never get here.
+	  s << "sub " << Register::toString(p_reg1) << "," << (-p_constant);
+	}
+	instr = addNewAssembly(instr, s.str());
+	if (p_annotation.isSigned())
+	{
+		instr = addNewAssembly(instr, "jno 0x22");
+		instr->setFallthrough(saturation_policy);
+		instr->setTarget(restore);
+	}
+	else if (p_annotation.isUnsigned())
+	{
+		instr = addNewAssembly(instr, "jnc 0x22");
+		instr->setFallthrough(saturation_policy);
+		instr->setTarget(restore);
+	}
+	else
+	{
+		Instruction_t *instr2 = addNewAssembly(instr, "jno 0x22");
+		instr2->setTarget(restore);
+		instr = addNewAssembly(instr2, "jnc 0x22");
+		instr->setFallthrough(saturation_policy);
+		instr->setTarget(restore);
+	}
+
+	// <policy>                  
+	//         nop                    ;
+	//         () callback handler    ;
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//            fallthrough-->originalNext (if no saturation)
+	//         saturateMax(r3)        ; optional saturation
+	//            fallthrough-->originalNext
+	//
+	// assume 64 bit for now
+	//
+	Instruction_t *popf = addNewAssembly("popf");
+	Instruction_t *callback = addCallbackHandlerSequence(p_instruction, popf, OVERFLOW64_DETECTOR, p_policy);
+	saturation_policy->setFallthrough(callback);
+	instr = addNewAssembly(popf, "pop " + Register::toString(p_reg1));
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		instr = addNewMaxSaturation(instr, p_reg3, p_annotation);
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(origFallthrough);
+	}
+	else
+	{
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(originalInstrumentInstr);
+	}
+
+	// <restore>
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//
+	// <orig>: lea r3, [r1+k]         ; original instruction        
+	//         <originalNext>         ; original next instruction
+	//
+	restore->setComment("lea overflow instrumentation(reg+k): restore");
+	instr = addNewAssembly(restore, "pop " + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+	instr->setFallthrough(originalInstrumentInstr);
+	originalInstrumentInstr->setFallthrough(origFallthrough);
+}
+
+
+// Example annotation to handle
+// 804852e      3 INSTR CHECK OVERFLOW NOFLAGSIGNED 32 EDX+EAX ZZ lea     eax, [edx+eax] Reg1: EDX Reg2: EAX
+// Need to handle both 32-bit and 64-bit versions
+//
+// Original:
+//   lea r3, [r1*k]
+//   <originalNext>
+//
+// Instrumentation:
+//   push r1                ;   save r1
+//   pushf                  ;   save flags
+//   imul r1, r2            ;   r1 = r1 * r2
+//        <overflowcheck>   ;   check for overflow 
+//          (jno <restore>) ; 
+//            fallthrough--><policy>
+//
+// <restore>
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//
+// <orig>: lea r3, [r1*k]        ; original instruction        
+//         <originalNext>         ; original next instruction
+//
+// <policy>                  
+//         () callback handler 
+//         popf                   ; restore flags
+//         pop r1                 ; restore register
+//            fallthrough-->originalNext (if no saturation)
+//         saturateMax(r3)        ; optional saturation
+//            fallthrough-->originalNext
+//
+void IntegerTransform64::addOverflowCheckNoFlag_RegTimesConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const int p_constant, const RegisterName& p_reg3, int p_policy)
+{
+	assert(p_instruction && p_instruction->getFallthrough());
+
+	cerr << __func__ << ": r3 <-- r1*k: r1: " << Register::toString(p_reg1) << " k: " << p_constant << " target register: " << Register::toString(p_reg3) << "  annotation: " << p_annotation.toString() << endl;
+
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+	Instruction_t *instr, *first, *saturation_policy;
+	Instruction_t *restore = addNewAssembly("popf");
+	saturation_policy = addNewAssembly("nop");
+	saturation_policy->setComment("lea overflow instrumentation(reg*k): policy code sequence");
+
+	// Original code sequence:
+	//   lea r3, [r1*k]
+	//   <originalNext>
+	//
+	// Instrumentation:
+	//   push r1                ;   save r1
+	//   pushf                  ;   save flags
+	//   imul r1, k            ;   r1 = r1 * k
+	//        <overflowcheck>   ;   check for overflow 
+	//        jno <restore>     ; 
+	//           fallthrough--><policy>
+	//
+	/*
+	first = addNewAssembly("push " + Register::toString(p_reg1)); 
+	first->setComment("lea overflow instrumentation(reg*k): start");
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, first);
+	instr = addNewAssembly(first, "pushf");
+	*/
+
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, "lea rsp, [rsp-128]" , NULL);
+	p_instruction->setComment("lea overflow instrumentation(reg*k): start");
+	instr = addNewAssembly(p_instruction, std::string("push ") + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "pushf");
+/*--------------*/
+	// make sure we set the fallthrough post careful insertion
+//	first->setFallthrough(instr);
+
+	std::ostringstream s;
+	s << "imul " << Register::toString(p_reg1) << "," << p_constant;
+	instr = addNewAssembly(instr, s.str());
+	instr = addNewAssembly(instr, "jno 0x22");
+	instr->setFallthrough(saturation_policy);
+	instr->setTarget(restore);
+
+	// <policy>                  
+	//         nop                    ;
+	//         () callback handler    ;
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//            fallthrough-->originalNext (if no saturation)
+	//         saturateMax(r3)        ; optional saturation
+	//            fallthrough-->originalNext
+	//
+	// assume 64 bit for now
+	//
+	Instruction_t *popf = addNewAssembly("popf");
+	Instruction_t *callback = addCallbackHandlerSequence(p_instruction, popf, OVERFLOW64_DETECTOR, p_policy);
+	saturation_policy->setFallthrough(callback);
+	instr = addNewAssembly(popf, "pop " + Register::toString(p_reg1));
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		instr = addNewMaxSaturation(instr, p_reg3, p_annotation);
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(origFallthrough);
+	}
+	else
+	{
+		instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+		instr->setFallthrough(originalInstrumentInstr);
+	}
+
+	// <restore>
+	//         popf                   ; restore flags
+	//         pop r1                 ; restore register
+	//
+	// <orig>: lea r3, [r1*k]        ; original instruction        
+	//         <originalNext>         ; original next instruction
+	//
+	restore->setComment("lea overflow instrumentation(reg*reg): restore");
+	instr = addNewAssembly(restore, "pop " + Register::toString(p_reg1));
+	instr = addNewAssembly(instr, "lea rsp, [rsp+128]");
+	instr->setFallthrough(originalInstrumentInstr);
+	originalInstrumentInstr->setFallthrough(origFallthrough);
+}
+
+//
+// STARS has extensive discussion of the logic behind truncation and
+//  signedness annotations in module SMPInstr.cpp, method EmitIntegerErrorAnnotation().
+//  The possible combinations are categorized in terms of the instrumentation
+//  needed at run time:
+//  CHECK TRUNCATION UNSIGNED:    discarded bits must be all zeroes.
+//  CHECK TRUNCATION SIGNED:      discarded bits must be sign-extension of stored bits.
+//  CHECK TRUNCATION UNKNOWNSIGN: discarded bits must be all zeroes, OR must
+//                                  be the sign-extension of the stored bits.
+// All truncation annotations are emitted on stores (mov opcodes in x86).
+// Other possibilities might be handled in the future.
+//
+
+bool IntegerTransform64::addTruncationCheck32(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(p_instruction && p_instruction->getFallthrough() &&
+		p_annotation.getTruncationFromWidth() == 32 && 
+		(p_annotation.getTruncationToWidth() == 16 || p_annotation.getTruncationToWidth() == 8) &&
+		isMovInstruction(p_instruction));
+
+	// Complicated case:
+	// 80484ed 3 INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+	//  example: for unknownsign truncation - 8 bit on AL
+	//          it's ok if 24 upper bits are sign-extension or all 0's
+	//          Re-phrased: upper 24 are 0s, upper 25 are 0s, upper 25 are 1s
+	//           are all OK in the UNKNOWNSIGN case
+	//          Note that upper 24 are 0's means no need to check for the
+	//           case where the upper 25 are 0's; already OK.
+	//
+	//             <save flags>
+	//             test eax, 0xFFFFFF00   ; (for 8 bit) 
+	//             jz <continue>          ; upper 24 bits are 0's 
+	//
+	//             cmp eax, 0xFFFFFF80    ;(for 8 bit) 
+	//             jae continue           ; upper 25 bits are 1's
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   saturating-arithmetic  ; optional
+	//
+	// continue:   <restore flags>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	//
+
+	// Unsigned case:
+	// 80484ed 3 INSTR CHECK TRUNCATION UNSIGNED 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+	//  example: for unsigned truncation - 8 bit on AL
+	//          it's ok if 24 upper bits are all 0's
+	//
+	//             <save flags>
+	//             test eax, 0xFFFFFF00   ; (for 8 bit) 
+	//             jz <continue>          ; upper 24 bits are 0's 
+	//
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   saturating-arithmetic  ; optional
+	//
+	// continue:   <restore flags>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	//
+
+	string detector;
+	unsigned mask = 0, mask2 = 0;
+	string saturationValue = "0x0";
+
+	p_instruction->setComment("monitor for truncation32");
+
+	if (p_annotation.getTruncationToWidth() == 16) 
+	{
+		mask = 0xFFFF0000;
+		mask2 = 0xFFFF8000;
+
+		if(p_annotation.flowsIntoCriticalSink())
+		{
+			detector = TRUNCATION64_FORCE_EXIT;
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			saturationValue = "0xFFFF";
+			detector = string(TRUNCATION64_DETECTOR_UNSIGNED_32_16);
+		}
+		else if (p_annotation.isSigned())
+		{
+			saturationValue = "0x7FFF";
+			detector = string(TRUNCATION64_DETECTOR_SIGNED_32_16);
+		}
+		else
+		{
+			saturationValue = "0x7FFF";
+			detector = string(TRUNCATION64_DETECTOR_UNKNOWN_32_16);
+		}
+	}
+	else if (p_annotation.getTruncationToWidth() == 8) 
+	{
+		mask = 0xFFFFFF00;
+		mask2 = 0xFFFFFF80;
+		if(p_annotation.flowsIntoCriticalSink())
+		{
+			detector = TRUNCATION64_FORCE_EXIT;
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			saturationValue = "0xFF";
+			detector = string(TRUNCATION64_DETECTOR_UNSIGNED_32_8);
+		}
+		else if (p_annotation.isSigned())
+		{
+			saturationValue = "0x7F";
+			detector = string(TRUNCATION64_DETECTOR_SIGNED_32_8);
+		}
+		else
+		{
+			saturationValue = "0x7F";
+			detector = string(TRUNCATION64_DETECTOR_UNKNOWN_32_8);
+		}
+	}
+
+	//             <save flags>
+	//             test eax, 0xFFFFFF00   ; (for 8 bit) 
+	//             jz <continue>          ; upper 24 bits are 0's 
+	//
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   mov [ebp+var_4], <saturate> ; optional
+    //             jmp origFT
+	//
+	// continue:   <restore flags>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	// origFT:     <originalFallThroughInstruction>
+	//
+
+	char buf[MAX_ASSEMBLY_SIZE];
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+	Instruction_t *instr, *save, *test;
+	Instruction_t *restore = addNewAssembly("popf");
+	restore->setComment("trunc: restore flags");
+
+/*
+	save = addNewAssembly("pushf");
+	save->setComment("start truncation sequence");
+*/
+
+	if (p_annotation.isSigned())
+	{
+		sprintf(buf, "test %s, 0x%8x", Register::toString(p_annotation.getRegister()).c_str(), mask2);
+	}
+	else
+	{
+		sprintf(buf, "test %s, 0x%8x", Register::toString(p_annotation.getRegister()).c_str(), mask);
+	}
+	logMessage(__func__, buf);
+
+/*
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, save);
+	test = addNewAssembly(save, buf);
+*/
+/*--------------*/
+//	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, std::string("pushf"), NULL);
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, "lea rsp, [rsp-128]" , NULL);
+	p_instruction->setComment("start truncation sequence");
+	instr = addNewAssembly(p_instruction, "pushf");
+	test = addNewAssembly(instr, buf);
+/*--------------*/
+ //   p_instruction->setFallthrough(test);
+
+//	save->setFallthrough(test);
+
+    instr = addNewAssembly(restore, "lea rsp, [rsp+128]");
+	instr->setFallthrough(originalInstrumentInstr);
+
+	if (p_annotation.isUnsigned())
+	{
+		logMessage(__func__, "unsigned annotation");
+		Instruction_t *nop = addNewAssembly("nop");
+
+		instr = addNewAssembly(test, "jz 0x22"); // bogus jump target for now
+		instr->setTarget(restore);
+		instr->setFallthrough(nop);
+	
+		Instruction_t *callback; 
+
+		if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+		{
+			string saturationInstruction = "mov " + p_annotation.getTarget2() + ", " + saturationValue;
+			Instruction_t *saturation = addNewAssembly(saturationInstruction);
+			saturation->setComment("trunc/unsigned/saturate");
+			
+			callback = addCallbackHandlerSequence(p_instruction, saturation, detector, p_policy);
+			nop->setFallthrough(callback);
+			saturation->setFallthrough(restore);
+		}
+		else
+		{
+			callback = addCallbackHandlerSequence(p_instruction, restore, detector, p_policy);
+			nop->setFallthrough(callback);
+		}
+	}
+	else
+	{
+		// Signed and unknown signed cases are almost identical:
+		// 80484ed 3 INSTR CHECK TRUNCATION SIGNED 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+		// 80484ed 3 INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+		//  example: for signed truncation - 8 bit on AL
+		//          it's ok if 25 upper bits are all 1's or all 0's
+		//  example: for unknownsign truncation - 8 bit on AL
+		//          it's ok if 25 upper bits are all 1's or 24 upper bits all 0's
+		//
+		//             <save flags>
+		//             test eax, 0xFFFFFF80   ; (for 8 bit) 0xFFFFFF00 for UNKNOWN
+		//             jz <continue>          ; upper 25 bits are 0's 
+		//
+		//             cmp eax, 0xFFFFFF80    ;(for 8 bit) 
+		//             jae continue           ; upper 25 bits are 1's
+		//             (invoke truncation handler) 
+		//             nop ; truncation handler callback here
+		//      SAT:   saturating-arithmetic  ; optional
+		//
+		// continue:   <restore flags>
+		//             mov [ebp+var_4], al    ; <originalInstruction>
+		//
+		logMessage(__func__, "signed/unknown annotation");
+		Instruction_t *nop = addNewAssembly("nop");
+
+		instr = addNewAssembly(test, "jz 0x22"); // bogus jump target for now
+		instr->setTarget(restore);
+		
+		std::ostringstream s;
+		s << "cmp " << Register::toString(p_annotation.getRegister()) << ", 0x" << hex << mask2 << dec;
+		instr = addNewAssembly(instr, s.str());
+
+		instr = addNewAssembly(instr, "jae 0x22"); 
+		instr->setTarget(restore);
+		instr->setFallthrough(nop);
+
+		Instruction_t *callback; 
+
+		if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+		{
+			string saturationInstruction = "mov " + p_annotation.getTarget2() + ", " + saturationValue;
+			Instruction_t *saturation = addNewAssembly(saturationInstruction);
+			if (p_annotation.isSigned())
+				saturation->setComment("trunc/signed/saturate");
+			else
+				saturation->setComment("trunc/unknown/saturate");
+			
+			callback = addCallbackHandlerSequence(p_instruction, saturation, detector, p_policy);
+			nop->setFallthrough(callback);
+			saturation->setFallthrough(restore);
+		}
+		else
+		{
+			callback = addCallbackHandlerSequence(p_instruction, restore, detector, p_policy);
+			nop->setFallthrough(callback);
+		}
+	}
+
+	return true;
+}
+
+//    we want:  32->16  movzx edx, ax -->  movzx edx, 0xFFFF
+//              32->8   movzx edx, al -->  movzx edx, 0xFF
+//
+// let's handle 2-operand instructions of the form:
+//            mov *, <reg>
+//
+
+string IntegerTransform64::buildSaturationAssembly(Instruction_t *p_instruction, string p_pattern, string p_value)
+{
+	// @todo: verify 2 operands!
+
+	string i = p_instruction->getDisassembly();
+
+	convertToLowercase(i);
+	convertToLowercase(p_pattern);
+	convertToLowercase(p_value);
+
+	size_t commaPos = i.find_last_of(',');
+	if (commaPos != string::npos)
+		i.replace(i.find(p_pattern, commaPos), p_pattern.size(), p_value);
+	else
+		i.replace(i.find(p_pattern), p_pattern.size(), p_value);
+	return i;
+}
+
+//
+// STARS has extensive discussion of the logic behind truncation and
+//  signedness annotations in module SMPInstr.cpp, method EmitIntegerErrorAnnotation().
+//  The possible combinations are categorized in terms of the instrumentation
+//  needed at run time:
+//  CHECK TRUNCATION UNSIGNED:    discarded bits must be all zeroes.
+//  CHECK TRUNCATION SIGNED:      discarded bits must be sign-extension of stored bits.
+//  CHECK TRUNCATION UNKNOWNSIGN: discarded bits must be all zeroes, OR must
+//                                  be the sign-extension of the stored bits.
+// All truncation annotations are emitted on stores (mov opcodes in x86).
+// Other possibilities might be handled in the future.
+//
+
+bool IntegerTransform64::addTruncationCheck64(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	assert(p_instruction && p_instruction->getFallthrough() &&
+		p_annotation.getTruncationFromWidth() == 64 && 
+		(p_annotation.getTruncationToWidth() == 32 || p_annotation.getTruncationToWidth() == 16 || p_annotation.getTruncationToWidth() == 8) &&
+		isMovInstruction(p_instruction));
+
+	std::set<RegisterName> takenRegs;
+	takenRegs.insert(p_annotation.getRegister()); 
+	takenRegs.insert(p_annotation.getRegister2());
+	takenRegs.insert(rn_RSP); // don't mess with the stack pointer
+	takenRegs.insert(rn_RBP); // don't mess with the frame pointer
+	RegisterName borrowReg = Register::getFreeRegister64(takenRegs);
+
+	if (borrowReg == rn_UNKNOWN)
+	{
+		logMessage(__func__, "Could not borrow a 64-bit register");
+		return false;
+	}
+
+	// Main difference between TRUNCATION annotation for 64 bits vs. 32 bits
+	// is that we need to use a register as IA X86-64 doesn't support 64 bit constants
+	// for most instructions
+
+	// Complicated case:
+	// 80484ed 3 INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+	//  example: for unknownsign truncation - 8 bit on AL
+	//          it's ok if 24 upper bits are sign-extension or all 0's
+	//          Re-phrased: upper 24 are 0s, upper 25 are 0s, upper 25 are 1s
+	//           are all OK in the UNKNOWNSIGN case
+	//          Note that upper 24 are 0's means no need to check for the
+	//           case where the upper 25 are 0's; already OK.
+	//
+	//             <save reg>
+	//             <save flags>
+	//             mov <reg>, 0xFFFFFFFFFFFFFF00  ; // need to grab register 
+	//             test eax, <reg>        ; (for 8 bit) 
+	//             jz <continue>          ; upper 56 bits are 0's 
+	//
+	//             cmp eax, 0xFFFFFFFFFFFFFF80    ; (for 8 bit) 
+	//             jae continue           ; upper 57 bits are 1's
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   saturating-arithmetic  ; optional
+	//
+	// continue:   <restore flags>
+	//             <restore reg>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	//
+
+	// Unsigned case:
+	// 80484ed 3 INSTR CHECK TRUNCATION UNSIGNED 64 RAX 32 EAX ZZ mov     [ebp+var_4], al
+	//
+	//             <save reg>
+	//             <save flags>
+	//             mov <reg>, 0xFFFFFFFFFFFFFF00  ; // need to grab register 
+	//             test eax, <reg>; (for 64->32 bit) 
+	//             jz <continue>          ; upper 32 bits are 0's 
+	//
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   saturating-arithmetic  ; optional
+	//
+	// continue:   <restore flags>
+	//             <restore reg>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	//
+
+	string detector;
+	long long unsigned mask = 0, mask2 = 0;
+	string saturationValue = "0x0";
+
+	p_instruction->setComment("monitor for truncation64");
+
+	if (p_annotation.getTruncationToWidth() == 32) 
+	{
+		mask  = 0xFFFFFFFF00000000;
+		mask2 = 0xFFFFFFFF80000000;
+
+		if(p_annotation.flowsIntoCriticalSink())
+		{
+			detector = TRUNCATION64_FORCE_EXIT;
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			saturationValue = "0xFFFFFFFF";
+			detector = string(TRUNCATION64_DETECTOR_UNSIGNED_64_32);
+		}
+		else if (p_annotation.isSigned())
+		{
+			saturationValue = "0x7FFFFFFF";
+			detector = string(TRUNCATION64_DETECTOR_SIGNED_64_32);
+		}
+		else
+		{
+			saturationValue = "0x7FFFFFFF";
+			detector = string(TRUNCATION64_DETECTOR_UNKNOWN_64_32);
+		}
+	}
+	else if (p_annotation.getTruncationToWidth() == 16) 
+	{
+		mask  = 0xFFFFFFFFFFFF0000;
+		mask2 = 0xFFFFFFFFFFFF8000;
+
+		if(p_annotation.flowsIntoCriticalSink())
+		{
+			detector = TRUNCATION64_FORCE_EXIT;
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			saturationValue = "0xFFFF";
+			detector = string(TRUNCATION64_DETECTOR_UNSIGNED_64_16);
+		}
+		else if (p_annotation.isSigned())
+		{
+			saturationValue = "0x7FFF";
+			detector = string(TRUNCATION64_DETECTOR_SIGNED_64_16);
+		}
+		else
+		{
+			saturationValue = "0x7FFF";
+			detector = string(TRUNCATION64_DETECTOR_UNKNOWN_64_16);
+		}
+	}
+	else if (p_annotation.getTruncationToWidth() == 8) 
+	{
+		mask  = 0xFFFFFFFFFFFFFF00;
+		mask2 = 0xFFFFFFFFFFFFFF80;
+		if(p_annotation.flowsIntoCriticalSink())
+		{
+			detector = TRUNCATION64_FORCE_EXIT;
+		}
+		else if (p_annotation.isUnsigned())
+		{
+			saturationValue = "0xFF";
+			detector = string(TRUNCATION64_DETECTOR_UNSIGNED_64_8);
+		}
+		else if (p_annotation.isSigned())
+		{
+			saturationValue = "0x7F";
+			detector = string(TRUNCATION64_DETECTOR_SIGNED_64_8);
+		}
+		else
+		{
+			saturationValue = "0x7F";
+			detector = string(TRUNCATION64_DETECTOR_UNKNOWN_64_8);
+		}
+	}
+
+	//             <save reg>
+	//             <save flags>
+	//             mov <reg>, 0xFFFFFFFFFFFFFF00  ; // need to grab register 
+	//             test eax, <reg>        ; (for 8 bit) 
+	//             jz <continue>          ; upper 24 bits are 0's 
+	//
+	//             (invoke truncation handler)
+	//             nop ; truncation handler returns here
+	//      SAT:   mov [ebp+var_4], <saturate> ; optional
+	//             jmp origFT
+	//
+	// continue:   <restore flags>
+	//             <restore reg>
+	//             mov [ebp+var_4], al    ; <originalInstruction>
+	// origFT:     <originalFallThroughInstruction>
+	//
+
+	char buf[MAX_ASSEMBLY_SIZE];
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+	Instruction_t *instr, *save, *test, *pushf;
+	Instruction_t *restore = addNewAssembly("popf");
+	restore->setComment("trunc: restore flags");
+	Instruction_t *restoreReg = addNewAssembly("pop " + Register::toString(borrowReg));
+
+/*
+	save = addNewAssembly("push " + Register::toString(borrowReg));
+	save->setComment("start truncation sequence");
+
+	pushf = addNewAssembly(save, "pushf");
+
+	if (p_annotation.isSigned())
+		sprintf(buf, "mov %s, 0x%16llx", Register::toString(borrowReg).c_str(), mask2);
+	else
+		sprintf(buf, "mov %s, 0x%16llx", Register::toString(borrowReg).c_str(), mask);
+
+	instr = addNewAssembly(pushf, buf);
+
+	sprintf(buf, "test %s, %s", Register::toString(p_annotation.getRegister()).c_str(), Register::toString(borrowReg).c_str());
+
+*/
+
+/*
+	Instruction_t* originalInstrumentInstr = carefullyInsertBefore(p_instruction, save);
+	test = addNewAssembly(instr, buf);
+	*/
+/*--------------*/
+//	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, std::string("push ") + Register::toString(borrowReg), NULL);
+//	Instruction_t* lea = addNewAssembly("lea rsp, [rsp-128]");  // red zone 
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, "lea rsp, [rsp-128]" , NULL);
+	p_instruction->setComment("start truncation sequence");
+	instr = addNewAssembly(p_instruction, std::string("push ") + Register::toString(borrowReg));
+	instr = addNewAssembly(instr, "pushf");
+	if (p_annotation.isSigned())
+		sprintf(buf, "mov %s, 0x%16llx", Register::toString(borrowReg).c_str(), mask2);
+	else
+		sprintf(buf, "mov %s, 0x%16llx", Register::toString(borrowReg).c_str(), mask);
+	instr = addNewAssembly(instr, buf);
+	sprintf(buf, "test %s, %s", Register::toString(p_annotation.getRegister()).c_str(), Register::toString(borrowReg).c_str());
+	test = addNewAssembly(instr, buf);
+	//             <save reg>
+	//             <save flags>
+	//             mov <reg>, 0xFFFFFFFFFFFFFF00  ; // need to grab register 
+	//             test eax, <reg>        ; (for 8 bit) 
+/*--------------*/
+
+//	save->setFallthrough(pushf);
+
+    restore->setFallthrough(restoreReg);
+	instr = addNewAssembly(restoreReg, "lea rsp, [rsp+128]");
+	instr->setFallthrough(originalInstrumentInstr);
+
+	if (p_annotation.isUnsigned())
+	{
+		logMessage(__func__, "unsigned annotation");
+		Instruction_t *nop = addNewAssembly("nop");
+
+		instr = addNewAssembly(test, "jz 0x22"); // bogus jump target for now
+		instr->setTarget(restore);
+		instr->setFallthrough(nop);
+	
+		Instruction_t *callback; 
+
+		if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+		{
+			string saturationInstruction = "mov " + p_annotation.getTarget2() + ", " + saturationValue;
+			Instruction_t *saturation = addNewAssembly(saturationInstruction);
+			saturation->setComment("trunc/unsigned/saturate");
+			
+			callback = addCallbackHandlerSequence(p_instruction, saturation, detector, p_policy);
+			nop->setFallthrough(callback);
+			saturation->setFallthrough(restore);
+		}
+		else
+		{
+			callback = addCallbackHandlerSequence(p_instruction, restore, detector, p_policy);
+			nop->setFallthrough(callback);
+		}
+	}
+	else
+	{
+		// Signed and unknown signed cases are almost identical:
+		// 80484ed 3 INSTR CHECK TRUNCATION SIGNED 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+		// 80484ed 3 INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 8 AL ZZ mov     [ebp+var_4], al
+		//  example: for signed truncation - 8 bit on AL
+		//          it's ok if 25 upper bits are all 1's or all 0's
+		//  example: for unknownsign truncation - 8 bit on AL
+		//          it's ok if 25 upper bits are all 1's or 24 upper bits all 0's
+		//
+		//             <save reg>
+		//             <save flags>
+		//             mov <reg>, 0xFFFFFFFFFFFFFF80   
+		//             test eax, <reg> ; (for 8 bit) 0xFFFFFFFFFFFFFF00 for UNKNOWN
+		//             jz <continue>          ; upper 57 bits are 0's 
+		//
+		//             cmp eax,  0xFFFFFFFFFFFFFF80    ;(for 8 bit) 
+		//             jae continue           ; upper 57 bits are 1's
+		//             (invoke truncation handler) 
+		//             nop ; truncation handler callback here
+		//      SAT:   saturating-arithmetic  ; optional
+		//
+		// continue:   <restore flags>
+		//             <restore reg>
+		//             mov [ebp+var_4], al    ; <originalInstruction>
+		//
+		logMessage(__func__, "signed/unknown annotation");
+		Instruction_t *nop = addNewAssembly("nop");
+
+		instr = addNewAssembly(test, "jz 0x22"); // bogus jump target for now
+		instr->setTarget(restore);
+		
+		std::ostringstream s;
+		s << "mov " << Register::toString(borrowReg) << ", 0x" << hex << mask2 << dec;
+		instr = addNewAssembly(instr, s.str());
+
+		std::ostringstream s2;
+		s2 << "cmp " << Register::toString(p_annotation.getRegister()) << "," << Register::toString(borrowReg);
+		instr = addNewAssembly(instr, s2.str());
+
+		instr = addNewAssembly(instr, "jae 0x22"); 
+		instr->setTarget(restore);
+		instr->setFallthrough(nop);
+
+		Instruction_t *callback; 
+
+		if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+		{
+			string saturationInstruction = "mov " + p_annotation.getTarget2() + ", " + saturationValue;
+			Instruction_t *saturation = addNewAssembly(saturationInstruction);
+			if (p_annotation.isSigned())
+				saturation->setComment("trunc/signed/saturate");
+			else
+				saturation->setComment("trunc/unknown/saturate");
+			
+			callback = addCallbackHandlerSequence(p_instruction, saturation, detector, p_policy);
+			nop->setFallthrough(callback);
+			saturation->setFallthrough(restore);
+		}
+		else
+		{
+			callback = addCallbackHandlerSequence(p_instruction, restore, detector, p_policy);
+			nop->setFallthrough(callback);
+		}
+	}
+
+	return true;
+}
+
+// 8048576 5 INSTR CHECK SIGNEDNESS SIGNED 16 AX ZZ mov     [esp+28h], ax
+//             <save flags>
+//             TEST ax, ax
+//             jns L1
+//             invoke callback handler
+// (optional)  mov ax, MAX_16     ; saturating arithmetic (Max for bit width/sign/unsigned) 
+//  
+//       L1:   <restore flags>
+//             mov [esp+28h], ax
+//
+bool IntegerTransform64::addSignednessCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy)
+{
+	if (p_annotation.getRegister() == rn_UNKNOWN)
+		return false;
+
+	string detector = p_annotation.isSigned() ? SIGNEDNESS64_DETECTOR_SIGNED : SIGNEDNESS64_DETECTOR_UNSIGNED;
+	Instruction_t *origFallthrough = p_instruction->getFallthrough();
+
+	Instruction_t* originalInstrumentInstr = IRDBUtility::insertAssemblyBefore(getFileIR(), p_instruction, std::string("lea rsp, [rsp-128]"), NULL);
+	Instruction_t *save = addNewAssembly(p_instruction, "pushf");
+	// TEST <reg>, <reg>
+	std::ostringstream s;
+	s << "test " << Register::toString(p_annotation.getRegister()) << "," << Register::toString(p_annotation.getRegister());
+	Instruction_t *test = addNewAssembly(save, s.str());
+	originalInstrumentInstr->setFallthrough(origFallthrough);
+
+	Instruction_t *jns = addNewAssembly(test, "jns 0x22");
+	Instruction_t *nop = addNewAssembly(jns, "nop");
+	Instruction_t *restore = addNewAssembly("popf");
+	Instruction_t *learestore = addNewAssembly(restore, "lea rsp, [rsp+128]");
+	learestore->setFallthrough(originalInstrumentInstr);
+
+	jns->setTarget(restore);
+
+	Instruction_t *callback = NULL; 
+
+	if (p_policy == POLICY_CONTINUE_SATURATING_ARITHMETIC)
+	{
+		// what value should we saturate with for 64 and 32 bits?
+		Instruction_t *saturation = addNewMaxSaturation(nop, p_annotation.getRegister(), p_annotation);
+
+		if (p_annotation.isSigned())
+			saturation->setComment("signedness/signed/saturate");
+		else
+			saturation->setComment("signedness/unsigned/saturate");
+			
+		callback = addCallbackHandlerSequence(p_instruction, saturation, detector, p_policy);
+		nop->setFallthrough(callback);
+		saturation->setFallthrough(restore);
+	}
+	else
+	{
+		callback = addCallbackHandlerSequence(p_instruction, restore, detector, p_policy);
+		nop->setFallthrough(callback);
+	}
+	
+	return true;
+}
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform64.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform64.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..655042e99b4800d10d3e3183b60699ea582fdd6a
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/integertransform64.hpp
@@ -0,0 +1,92 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef _LIBTRANSFORM_INTEGERTRANSFORM64_H_
+#define _LIBTRANSFORM_INTEGERTRANSFORM64_H_
+
+#include "integertransform.hpp"
+
+namespace libTransform
+{
+
+using namespace std;
+using namespace libIRDB;
+
+class IntegerTransform64 : public IntegerTransform
+{
+	public:
+		IntegerTransform64(VariantID_t *, FileIR_t*, MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_warnings); 
+
+		virtual int execute();
+
+	protected:
+		virtual Instruction_t* addCallbackHandlerSequence(Instruction_t *p_orig, Instruction_t *p_fallthrough, std::string p_detector, int p_policy);
+		void handleOverflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleTruncation(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void handleSignedness(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		bool addOverflowUnderflowCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		void saturateSignedMultiplyOverflow(Instruction_t *p_orig, Instruction_t *p_instruction, Instruction_t* p_fallthrough);
+		bool addOverflowCheckNoFlag(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		void addOverflowCheckNoFlag_RegPlusReg(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const RegisterName& p_reg2, const RegisterName& p_reg3, int p_policy);
+		void addOverflowCheckNoFlag_RegTimesReg(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const RegisterName& p_reg2, const RegisterName& p_reg3, int p_policy);
+		void addOverflowCheckNoFlag_RegPlusConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const int p_constant, const RegisterName& p_reg3, int p_policy);
+		void addOverflowCheckNoFlag_RegTimesConstant(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, const RegisterName& p_reg1, const int p_constant, const RegisterName& p_reg3, int p_policy);
+		bool addTruncationCheck32(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		bool addTruncationCheck64(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+		bool addSignednessCheck(Instruction_t *p_instruction, const MEDS_InstructionCheckAnnotation& p_annotation, int p_policy);
+
+		string buildSaturationAssembly(Instruction_t *p_instruction, string p_pattern, string p_value);
+};
+
+
+} // end namespace
+
+#define OVERFLOW64_DETECTOR            "overflow_detector_64"
+#define UNDERFLOW64_DETECTOR           "underflow_detector_64"
+
+#define	TRUNCATION64_DETECTOR_UNSIGNED_64_32      "truncation_detector_64_32"
+#define	TRUNCATION64_DETECTOR_SIGNED_64_32        "truncation_detector_64_32"
+#define	TRUNCATION64_DETECTOR_UNKNOWN_64_32       "truncation_detector_64_32"
+
+#define	TRUNCATION64_DETECTOR_UNSIGNED_64_16      "truncation_detector_64_16"
+#define	TRUNCATION64_DETECTOR_SIGNED_64_16        "truncation_detector_64_16"
+#define	TRUNCATION64_DETECTOR_UNKNOWN_64_16       "truncation_detector_64_16"
+
+#define	TRUNCATION64_DETECTOR_UNSIGNED_64_8       "truncation_detector_64_8"
+#define	TRUNCATION64_DETECTOR_SIGNED_64_8         "truncation_detector_64_8"
+#define	TRUNCATION64_DETECTOR_UNKNOWN_64_8        "truncation_detector_64_8"
+
+#define	TRUNCATION64_DETECTOR_UNSIGNED_32_16      "truncation_detector_32_16"
+#define	TRUNCATION64_DETECTOR_SIGNED_32_16        "truncation_detector_32_16"
+#define	TRUNCATION64_DETECTOR_UNKNOWN_32_16       "truncation_detector_32_16"
+
+#define	TRUNCATION64_DETECTOR_UNSIGNED_32_8       "truncation_detector_32_8"
+#define	TRUNCATION64_DETECTOR_SIGNED_32_8         "truncation_detector_32_8"
+#define	TRUNCATION64_DETECTOR_UNKNOWN_32_8        "truncation_detector_32_8"
+
+#define	TRUNCATION64_FORCE_EXIT                   "truncation_force_exit"
+
+#define SIGNEDNESS64_DETECTOR_SIGNED              "signedness_detector_signed"
+#define SIGNEDNESS64_DETECTOR_UNSIGNED            "signedness_detector_unsigned"
+
+#endif
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/leapattern.cpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/leapattern.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d8a16c304346a126d88473b627dd2e001bc43248
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/leapattern.cpp
@@ -0,0 +1,233 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <iostream>
+#include <string.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <stdio.h>
+#include <sstream>
+
+#include "leapattern.hpp"
+
+using namespace std;
+using namespace libTransform;
+
+//
+// Supported patterns:
+//     reg+reg
+//     reg+k
+//     reg*reg
+//     reg*k
+//
+// Not (yet) supported:
+//     reg+reg+k
+//
+LEAPattern::LEAPattern(const MEDS_InstructionCheckAnnotation& p_annotation)
+{
+	m_isValid = false;
+	m_isRegPlusReg = false;
+	m_isRegPlusConstant = false;
+	m_isRegTimesConstant = false;
+	m_isRegTimesReg = false;
+	m_reg1 = rn_UNKNOWN;
+	m_reg2 = rn_UNKNOWN;
+	m_constant = 0;
+
+    if(regcomp(&m_regex_reg_plus_reg ,"[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]\\+[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]", REG_EXTENDED | REG_ICASE) !=0)
+	    cerr << "Error: regular expression for reg+reg failed" << endl;
+
+    if(regcomp(&m_regex_reg_times_reg ,"[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]\\*[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]", REG_EXTENDED | REG_ICASE) !=0)
+	    cerr << "Error: regular expression for reg*reg failed" << endl;
+
+    if(regcomp(&m_regex_reg_plus_constant ,"[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]\\+[0-9+]", REG_EXTENDED | REG_ICASE) !=0)
+	    cerr << "Error: regular expression for reg+constant failed" << endl;
+
+    if(regcomp(&m_regex_reg_plus_negconstant ,"[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]\\+\\-[0-9+]", REG_EXTENDED | REG_ICASE) !=0)
+	    cerr << "Error: regular expression for reg+constant failed" << endl;
+
+    if(regcomp(&m_regex_reg_times_constant ,"[eax|ebx|ecx|edx|esi|edi|ebp|rax|rbx|rcx|rdx|rbp|rsi|rdi|r8|r9|r10|r11|r12|r13|r14|r15]\\*[0-9+]", REG_EXTENDED | REG_ICASE) !=0)
+	    cerr << "Error: regular expression for reg+constant failed" << endl;
+
+	const int max = 5;
+	regmatch_t pmatch[max];
+	int countMatch = 0;
+
+	if(regexec(&m_regex_reg_plus_reg, p_annotation.getTarget().c_str(), max, pmatch, 0)==0)
+	{
+		// pattern is of the form reg+reg, e.g.:   EDX+EAX
+		//                                         r8+rbp
+		//                                         r8+r9
+		//                                         rax+r9
+		string r1, r2;
+		extractOperands(p_annotation.getTarget(), r1, r2);
+		cerr << "leapattern: extract ops: " << r1 << " " << r2 << endl;
+		m_reg1 = Register::getRegister(r1);
+		m_reg2 = Register::getRegister(r2);
+
+		if (m_reg1 != rn_UNKNOWN && m_reg2 != rn_UNKNOWN)
+		{
+			countMatch++;
+			m_isRegPlusReg = true;
+			m_isValid = true;
+			cerr << "leapattern: reg+reg:" << Register::toString(m_reg1) << " " << Register::toString(m_reg2) << endl;  
+		}
+	}
+    
+	if(regexec(&m_regex_reg_times_reg, p_annotation.getTarget().c_str(), max, pmatch, 0)==0)
+	{
+		// pattern is of the form reg*reg, e.g.:   EDX*EAX
+		// nb: is this even a valid pattern -- not used 
+		string r1, r2;
+		extractOperands(p_annotation.getTarget(), r1, r2);
+		m_reg1 = Register::getRegister(r1);
+		m_reg2 = Register::getRegister(r2);
+		cerr << "leapattern: extract ops: " << r1 << " " << r2 << endl;
+
+		if (m_reg1 != rn_UNKNOWN && m_reg2 != rn_UNKNOWN)
+		{
+			countMatch++;
+			m_isRegTimesReg = true;
+			m_isValid = true;
+			cerr << "leapattern: reg*reg:" << Register::toString(m_reg1) << " " << Register::toString(m_reg2) << endl;  
+		}
+	}
+	
+// integertransform: reg+constant: register: EDX constant: 80 target register: EAX  annotation:    805525b      6 INSTR CHECK OVERFLOW NOFLAGUNSIGNED 32 EDX+128 ZZ lea     eax, [edx+80h]
+
+	if(regexec(&m_regex_reg_plus_constant, p_annotation.getTarget().c_str(), max, pmatch, 0)==0 ||
+	        regexec(&m_regex_reg_plus_negconstant, p_annotation.getTarget().c_str(), max, pmatch, 0)==0)
+	{
+		// pattern is of the form: reg+constant, e.g.: EDX+16
+		// pattern is of the form: reg+-constant, e.g.: EAX+-16
+		// note that constant value of annotation is in decimal (not hex)
+		string r1, k;
+		extractOperands(p_annotation.getTarget(), r1, k);
+		m_reg1 = Register::getRegister(r1);
+		cerr << "leapattern: extract ops: " << r1 << " " << k << endl;
+
+		stringstream constantSS(k);
+		if (constantSS >> m_constant)
+		{
+			m_isRegPlusConstant = true;
+			m_isValid = true;
+			countMatch++;
+			cerr << "leapattern: reg+-constant: stream: " << Register::toString(m_reg1) << " constant: " << dec << m_constant << " annotation: " << p_annotation.toString() << endl;
+		}
+	}
+	
+	if(regexec(&m_regex_reg_times_constant, p_annotation.getTarget().c_str(), max, pmatch, 0)==0)
+	{
+		// pattern is of the form: reg*constant, e.g.: EDX*4
+		// note that constant value of annotation is in decimal (not hex)
+		string r1, k;
+		extractOperands(p_annotation.getTarget(), r1, k);
+		cerr << "leapattern: extract ops: " << r1 << " " << k << endl;
+		m_reg1 = Register::getRegister(r1);
+		stringstream constantSS(k);
+		if (constantSS >> m_constant)
+		{
+			countMatch++;
+			cerr << "leapattern: reg*constant: stream: " << p_annotation.getTarget().substr(4) << " constant: " << dec << m_constant << " annotation: " << p_annotation.toString() << endl;
+			m_isValid = true;
+			m_isRegTimesConstant = true;
+		}
+	}
+
+	if (countMatch == 0 || countMatch > 1)
+	{
+		cerr << "leapattern: matching patterns = " << countMatch << " : " << p_annotation.toString() << endl;
+		m_isValid = false;
+	}
+}
+
+bool LEAPattern::isValid() const
+{
+	return m_isValid;
+}
+
+bool LEAPattern::isRegisterPlusRegister() const
+{
+	return m_isRegPlusReg;
+}
+
+bool LEAPattern::isRegisterTimesRegister() const
+{
+	return m_isRegTimesReg;
+}
+
+bool LEAPattern::isRegisterPlusConstant() const
+{
+	return m_isRegPlusConstant;
+}
+
+bool LEAPattern::isRegisterTimesConstant() const
+{
+	return m_isRegTimesConstant;
+}
+
+RegisterName LEAPattern::getRegister1() const
+{
+	return m_reg1;
+}
+
+RegisterName LEAPattern::getRegister2() const
+{
+	return m_reg2;
+}
+
+int LEAPattern::getConstant() const
+{
+	return m_constant;
+}
+
+// assume is of the form:
+//       <operand><sign>[minus]<operand>
+// where <operand> is a register or constant,
+//       <sign> is * or +
+void LEAPattern::extractOperands(const string target, string& op1, string& op2)
+{
+	int multiplyPos = target.find('*');
+	int plusPos = target.find('+');
+	int minusPos = target.find('-');
+
+	int signPos = -1;
+	if (multiplyPos >= 0) signPos = multiplyPos;
+	if (plusPos >= 0) signPos = plusPos;
+
+	op1 = op2 = "";
+
+	if (signPos < 0) return;
+
+	int op1len = signPos;
+	int op2len;
+	
+	if (minusPos >= 0) 
+			op2len = target.size() - minusPos - 1;
+	else
+			op2len = target.size() - signPos - 1;
+
+	op1 = target.substr(0, op1len);
+
+	if (minusPos >= 0) 
+		op2 = target.substr(signPos+2, op2len); // e.g., rax+-5
+	else
+		op2 = target.substr(signPos+1, op2len);
+}
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/leapattern.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/leapattern.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..7b25314ad9efba376deda26cb47a760d065b1ae8
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/leapattern.hpp
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef _LEA_PATTERN_H_
+#define _LEA_PATTERN_H_
+
+#include <regex.h>
+
+#include "MEDS_InstructionCheckAnnotation.hpp"
+#include "MEDS_Register.hpp"
+
+using namespace MEDS_Annotation;
+
+namespace libTransform {
+
+class LEAPattern {
+	public:
+		LEAPattern(const MEDS_InstructionCheckAnnotation& p_annotation);
+		bool isValid() const;
+
+		bool isRegisterPlusRegister() const;
+		bool isRegisterPlusConstant() const;
+		bool isRegisterTimesConstant() const; 
+		bool isRegisterTimesRegister() const; // not used
+
+		RegisterName getRegister1() const;
+		RegisterName getRegister2() const;
+		int getConstant() const;
+
+	private:
+		void extractOperands(const string target, string& op1, string& op2);
+
+	private:
+		bool                     m_isValid;
+		bool                     m_isRegPlusReg;
+		bool                     m_isRegPlusConstant;
+		bool                     m_isRegTimesReg;
+		bool                     m_isRegTimesConstant;
+		RegisterName   m_reg1;
+		RegisterName   m_reg2;
+		int                      m_constant;
+
+		regex_t                  m_regex_reg_plus_reg;
+		regex_t                  m_regex_reg_times_reg;
+		regex_t                  m_regex_reg_plus_constant;
+		regex_t                  m_regex_reg_plus_negconstant;
+		regex_t                  m_regex_reg_times_constant;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/pointercheck64.cpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/pointercheck64.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3c4ba7d64f82de8ecb949cf94719ef4d69e51ac4
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/pointercheck64.cpp
@@ -0,0 +1,150 @@
+/*
+ * Copyright (c) 2015 - Zephyr Software LLC
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software LLC
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <assert.h>
+#include <sstream>
+#include "pointercheck64.hpp"
+
+using namespace libTransform;
+
+
+PointerCheck64::PointerCheck64(VariantID_t *p_variantID, FileIR_t *p_fileIR, MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_benignFalsePositives) : IntegerTransform64(p_variantID, p_fileIR, p_annotations, p_filteredFunctions, p_benignFalsePositives)
+{
+}
+
+Instruction_t* PointerCheck64::addCallbackHandlerSequence(Instruction_t *p_orig, Instruction_t *p_fallthrough, std::string p_detector, int p_policy)
+{
+	if (p_policy == POLICY_EXIT)
+	{				
+		// exit program
+		Instruction_t* exit_sequence = addNewAssembly("mov rax, 60");
+		Instruction_t* i = addNewAssembly(exit_sequence, "mov rdi, 25");
+		i = addNewAssembly(i, "syscall");
+		i->setFallthrough(p_fallthrough); 
+		return exit_sequence;
+	}
+	else
+		return IntegerTransform64::addCallbackHandlerSequence(p_orig, p_fallthrough, p_detector, p_policy);
+}
+
+int PointerCheck64::execute()
+{
+	for(
+	  set<Function_t*>::const_iterator itf=getFileIR()->GetFunctions().begin();
+	  itf!=getFileIR()->GetFunctions().end();
+	  ++itf
+	  )
+	{
+		Function_t* func=*itf;
+
+		if (getFilteredFunctions()->find(func->GetName()) != getFilteredFunctions()->end())
+		{
+			logMessage(__func__, "filter out: " + func->GetName());
+			continue;
+		}
+
+		if (isBlacklisted(func))
+		{
+			logMessage(__func__, "blacklisted: " + func->GetName());
+			m_numBlacklisted++;
+			continue;
+		}
+
+		logMessage(__func__, "processing fn: " + func->GetName());
+
+		for(
+		  set<Instruction_t*>::const_iterator it=func->GetInstructions().begin();
+		  it!=func->GetInstructions().end();
+		  ++it)
+		{
+			Instruction_t* insn=*it;
+
+			if (insn && insn->getAddress())
+			{
+				int policy = POLICY_EXIT; 
+
+				virtual_offset_t irdb_vo = insn->getAddress()->GetVirtualOffset();
+				if (irdb_vo == 0) continue;
+
+				VirtualOffset vo(irdb_vo);
+
+				if (getAnnotations()->count(vo) == 0)
+					continue;
+
+				std::pair<MEDS_Annotations_t::iterator,MEDS_Annotations_t::iterator> ret;
+				ret = getAnnotations()->equal_range(vo);
+				MEDS_InstructionCheckAnnotation annotation; 
+				MEDS_InstructionCheckAnnotation* p_annotation; 
+				for ( MEDS_Annotations_t::iterator it = ret.first; it != ret.second; ++it)
+				{
+					MEDS_AnnotationBase *base_type=(it->second);
+					p_annotation = dynamic_cast<MEDS_InstructionCheckAnnotation*>(base_type);
+					if(p_annotation == NULL)
+						continue;
+					annotation = *p_annotation;
+					if (!annotation.isValid()) 
+						continue;
+					else
+						break; // let's just handle one annotation for now and see how it goes
+				}
+
+				m_numAnnotations++;
+
+				if (!annotation.isIdiom() || annotation.getIdiomNumber() != IDIOM_POINTER_NUMERIC_WEAKNESS)
+				{
+					logMessage(__func__, "skip IDIOM");
+					m_numIdioms++;
+					continue;
+				}
+
+				if (!insn->getFallthrough())
+				{
+					logMessage(__func__, "Warning: no fall through for instruction -- skipping");
+					continue;
+				}
+
+				if (annotation.isIdiom() && !isInstrumentIdioms())
+				{
+					logMessage(__func__, "skip IDIOM");
+					m_numIdioms++;
+					continue;
+				}
+
+				// this idiom deals with pointers ==> unsigned
+				if (!annotation.isUnsigned())
+				{							
+					logMessage(__func__, "Warning: only instrument UNSIGNED for this idiom -- skipping");
+					continue;
+				}
+ 
+				logMessage(__func__, annotation, "-- instruction: " + insn->getDisassembly());
+
+				if (annotation.isOverflow())
+				{
+					m_numTotalOverflows++;
+					handleOverflowCheck(insn, annotation, policy);
+				}
+
+				if (annotation.isUnderflow())
+				{
+					m_numTotalUnderflows++;
+					handleUnderflowCheck(insn, annotation, policy);
+				}
+			}
+		} // end iterate over all instructions in a function
+	} // end iterate over all functions
+
+	return 0;
+}
+
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/pointercheck64.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/pointercheck64.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..b7593b966a241e2b210dcc7d545de930390a7cc2
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/pointercheck64.hpp
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2015 - Zephyr Software LLC
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software LLC
+ * URL   : http://www.zephyr-software.com/
+ */
+
+#ifndef _LIBTRANSFORM_POINTERCHECK64_H_
+#define _LIBTRANSFORM_POINTERCHECK64_H_
+
+#include "integertransform64.hpp"
+
+namespace libTransform
+{
+
+using namespace std;
+using namespace libIRDB;
+
+class PointerCheck64 : public IntegerTransform64
+{
+	public:
+		PointerCheck64(VariantID_t *, FileIR_t*, MEDS_Annotations_t *p_annotations, set<std::string> *p_filteredFunctions, set<VirtualOffset> *p_warnings); 
+
+		virtual int execute();
+		virtual Instruction_t* addCallbackHandlerSequence(Instruction_t *p_orig, Instruction_t *p_fallthrough, std::string p_detector, int p_policy);
+
+};
+
+} // end namespace
+
+#endif
diff --git a/irdb-lib/libIRDB-transform/include-unused-delete-later/transform.hpp b/irdb-lib/libIRDB-transform/include-unused-delete-later/transform.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..325fa40d6e1ae85a3b92efa8b9ad6813543a453c
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/include-unused-delete-later/transform.hpp
@@ -0,0 +1,139 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef _LIBTRANSFORM_TRANSFORM_H
+#define _LIBTRANSFORM_TRANSFORM_H
+
+#include <string>
+#include <set>
+#include <map>
+
+#include <irdb-core>
+
+#include "MEDS_InstructionCheckAnnotation.hpp"
+#include "VirtualOffset.hpp"
+
+#define MAX_ASSEMBLY_SIZE 2048
+
+namespace libIRDB
+{
+	class FileIR_t;
+}
+namespace libTransform
+{
+using namespace std;
+using namespace IRDB_SDK;
+using namespace MEDS_Annotation;
+
+
+class Transform 
+{
+
+	public:
+		Transform(VariantID_t *, FileIR_t *, set<std::string> *p_filteredFunctions);
+
+	protected:
+		void setAssembly(Instruction_t *p_instr, string p_asm);
+		Instruction_t* addNewAssembly(string p_asm);
+		Instruction_t* addNewAssembly(Instruction_t *p_instr, string p_asm);
+		Instruction_t* registerCallbackHandler64(string p_callbackHandler, int p_numArgs);
+		void addCallbackHandler64(Instruction_t *p_instr, string p_callbackHandler, int p_numArgs);
+		void addInstruction(Instruction_t *p_instr, string p_dataBits, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		Instruction_t* carefullyInsertBefore(Instruction_t* &p_target, Instruction_t* &p_new);
+		Instruction_t* insertAssemblyBefore(Instruction_t* before, const string &the_asm, Instruction_t* target=nullptr);
+		Instruction_t* insertAssemblyAfter(Instruction_t* after, const string &the_asm, Instruction_t* target=nullptr);
+
+		void addPushRegister(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addPopRegister(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addPusha(Instruction_t *p_instr, Instruction_t *p_fallThrough);
+		void addPushf(Instruction_t *p_instr, Instruction_t *p_fallThrough);
+		void addPopa(Instruction_t *p_instr, Instruction_t *p_fallThrough);
+		void addPopf(Instruction_t *p_instr, Instruction_t *p_fallThrough);
+		void addNop(Instruction_t *p_instr, Instruction_t *p_fallThrough);
+
+		void addCallbackHandler(string p_detector, Instruction_t *p_instrumented, Instruction_t *p_instr, Instruction_t *p_fallThrough, int p_policy, AddressID_t *addressOriginal = NULL);
+
+		void addTestRegister(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addTestRegisterMask(Instruction_t *p_instr, RegisterName, unsigned p_mask, Instruction_t *p_fallThrough);
+		void addCmpRegisterMask(Instruction_t *p_instr, RegisterName, unsigned p_mask, Instruction_t *p_fallThrough);
+
+		void addJns(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJz(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJo(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJno(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJc(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJnc(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJnz(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addJae(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target);
+		void addNot(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addHlt(Instruction_t *p_instr, Instruction_t *p_fallThrough);
+
+		void addAddRegisters(Instruction_t *p_instr, RegisterName p_regTgt, RegisterName p_regSrc, Instruction_t *p_fallThrough);
+		void addAddRegisterConstant(Instruction_t *p_instr, RegisterName p_regTgt, int p_constantValue, Instruction_t *p_fallThrough);
+		void addMulRegisterConstant(Instruction_t *p_instr, RegisterName p_regTgt, int p_constantValue, Instruction_t *p_fallThrough);
+		void addMovRegisters(Instruction_t *p_instr, RegisterName p_regTgt, RegisterName p_regSrc, Instruction_t *p_fallThrough);
+
+		Instruction_t* allocateNewInstruction(DatabaseID_t p_fileID=BaseObj_t::NOT_IN_DATABASE, Function_t* p_func=NULL);
+
+		VirtualOffset_t getAvailableAddress();
+
+		VariantID_t* getVariantID() { return m_variantID; }
+		FileIR_t* getFileIR(); //  { return dynamic_cast<FileIR_t*>(m_fileIR); }
+		set<std::string>* getFilteredFunctions() { return m_filteredFunctions; }
+
+		Instruction_t* addNewMaxSaturation(Instruction_t *p_prev, RegisterName p_reg, const MEDS_InstructionCheckAnnotation p_annotation);
+		void addMinSaturation(Instruction_t *p_instruction, RegisterName p_reg, const MEDS_InstructionCheckAnnotation& p_annotation, Instruction_t *p_fallthrough);
+		void addMaxSaturation(Instruction_t *p_instruction, RegisterName p_reg, const MEDS_InstructionCheckAnnotation& p_annotation, Instruction_t *p_fallthrough);
+		void addMovRegisterUnsignedConstant(Instruction_t *p_instr, RegisterName p_regTgt, unsigned long p_constant, Instruction_t *p_fallThrough);
+		void addMovRegisterSignedConstant(Instruction_t *p_instr, RegisterName p_regTgt, long int p_constant, Instruction_t *p_fallThrough);
+		void addAndRegister32Mask(Instruction_t *p_instr, RegisterName p_regTgt, unsigned int p_mask, Instruction_t *p_fallThrough);
+
+	protected:
+		void logMessage(const std::string &p_method, const std::string &p_msg);
+		void logMessage(const std::string &p_method, const MEDS_InstructionCheckAnnotation&, const std::string &p_msg);
+
+	private:
+		void addTestRegister8(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addTestRegister16(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addTestRegister32(Instruction_t *p_instr, RegisterName, Instruction_t *p_fallThrough);
+		void addTestRegisterMask32(Instruction_t *p_instr, RegisterName, unsigned p_mask, Instruction_t *p_fallThrough);
+		void addCmpRegisterMask32(Instruction_t *p_instr, RegisterName, unsigned p_mask, Instruction_t *p_fallThrough);
+
+		VariantID_t 		*m_variantID;
+		libIRDB::FileIR_t       *m_fileIR;
+		set<std::string>	*m_filteredFunctions;
+		std::map<std::string, Instruction_t*> m_handlerMap;
+};
+
+// make sure these match values in detector_handlers.h in the strata library
+#define POLICY_DEFAULT                            0   
+#define POLICY_CONTINUE                           1  
+#define POLICY_EXIT                               2   
+#define POLICY_CONTINUE_SATURATING_ARITHMETIC     3   
+
+#define DEBUG_CALLBACK_HANDLER "debug_handler"
+
+// utility function
+void convertToLowercase(string&);
+
+}
+
+#endif
+
diff --git a/irdb-lib/libIRDB-transform/src/SConscript b/irdb-lib/libIRDB-transform/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..0c250bfeb153f70a9b77739937e968904158601a
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/src/SConscript
@@ -0,0 +1,31 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+files="rewrite_util.cpp  transform.cpp"
+
+cpppath='''
+         $IRDB_SDK/include
+         $SECURITY_TRANSFORMS_HOME/include
+         $SECURITY_TRANSFORMS_HOME/libIRDB-core/include
+         $SECURITY_TRANSFORMS_HOME/libIRDB-cfg/include
+         $SECURITY_TRANSFORMS_HOME/libIRDB-util/include
+         $SECURITY_TRANSFORMS_HOME/libMEDSannotation/include/
+        '''
+
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split("irdb-core irdb-cfg irdb-util MEDSannotation")
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS = " -std=c++11 ")
+
+lib=myenv.SharedLibrary("irdb-transform",  Split(files), LIBPATH=LIBPATH, LIBS=LIBS)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+Return('install')
+
diff --git a/irdb-lib/libIRDB-transform/src/SConstruct b/irdb-lib/libIRDB-transform/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..c96332f0422ad5df0853931209219d9a2e20bc17
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/src/SConstruct
@@ -0,0 +1,6 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
diff --git a/irdb-lib/libIRDB-transform/src/rewrite_util.cpp b/irdb-lib/libIRDB-transform/src/rewrite_util.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..443236f80fd64c1cda89e5171160824d553c1dd0
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/src/rewrite_util.cpp
@@ -0,0 +1,276 @@
+
+#include <irdb-transform>
+#include <libIRDB-core.hpp>
+
+// Copied from PnTransform
+// @todo: create a utility library with the one interface
+
+
+using namespace std;
+using namespace IRDB_SDK;
+
+void copyInstruction(Instruction_t* src, Instruction_t* dest);
+Instruction_t* copyInstruction(FileIR_t* virp, Instruction_t* instr);
+Instruction_t* allocateNewInstruction(FileIR_t* virp, DatabaseID_t p_fileID,Function_t* func);
+Instruction_t* allocateNewInstruction(FileIR_t* virp, Instruction_t *template_instr);
+
+
+
+void setInstructionsDetails(FileIR_t* virp, Instruction_t *p_instr, string p_dataBits, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+        if (p_instr == NULL) return;
+
+        p_instr->setDataBits(p_dataBits);
+        p_instr->setComment(p_instr->getDisassembly());
+        p_instr->setFallthrough(p_fallThrough);
+        p_instr->setTarget(p_target);
+
+	auto real_virp=dynamic_cast<libIRDB::FileIR_t*>(virp);
+	assert(real_virp);
+
+        real_virp->GetAddresses().insert(p_instr->getAddress());
+        real_virp->GetInstructions().insert(p_instr);
+}
+
+
+//For all insertBefore functions:
+//The "first" instruction will have its contents replaced and a duplicate of "first" will be in the follow of first. 
+//This duplicate is returned since the user already has a pointer to first.
+//To insert before an instruction is the same as modifying the original instruction, and inserting after it
+//a copy of the original instruction 
+Instruction_t* IRDB_SDK::insertAssemblyBefore(FileIR_t* virp, Instruction_t* first, string assembly, Instruction_t *target)
+{
+	Instruction_t* next = copyInstruction(virp,first);
+
+	//In case the fallthrough is null, generate spri has to have a 
+	//place to jump, which is determined by the original address.
+	//This code is not placed in copyInstruction since this is only needed
+	//when inserting before
+	next->setOriginalAddressID(first->getOriginalAddressID());
+	//"Null" out the original address (it should be as if the instruction was not in the database).
+	first->setOriginalAddressID(BaseObj_t::NOT_IN_DATABASE);
+	auto real_first=dynamic_cast<libIRDB::Instruction_t*>(first);
+	assert(real_first);
+	real_first->GetRelocations().clear();
+        first->setIBTargets(NULL);
+	//Note that the instruction just inserted should have the same exception handling
+        //info as the instructions immediately around it.
+        //Thus the exception handling information (EhCallSite and EhProgram) are kept the 
+        //same from the copy of first (unlike with relocations and IBT's).
+
+	virp->changeRegistryKey(first,next);
+	IRDB_SDK::setInstructionAssembly(virp,first,assembly,next,target);
+
+	return next;
+}
+
+#if 0
+Instruction_t* insertAssemblyBefore(FileIR_t* virp, Instruction_t* first, string assembly)
+{
+	return insertAssemblyBefore(virp,first,assembly,NULL);
+}
+
+
+Instruction_t* insertDataBitsBefore(FileIR_t* virp, Instruction_t* first, string dataBits)
+{
+        return insertDataBitsBefore(virp,first,dataBits,NULL);
+}
+#endif
+
+Instruction_t* IRDB_SDK::insertDataBitsBefore(FileIR_t* virp, Instruction_t* first, string dataBits, Instruction_t *target)
+{
+	Instruction_t* next = copyInstruction(virp,first);
+
+        //In case the fallthrough is null, generate spri has to have a 
+        //place to jump, which is determined by the original address.
+        //This code is not placed in copyInstruction since this is only needed
+        //when inserting before
+        next->setOriginalAddressID(first->getOriginalAddressID());
+        //"Null" out the original address (it should be as if the instruction was not in the database).
+        first->setOriginalAddressID(BaseObj_t::NOT_IN_DATABASE);
+	auto real_first=dynamic_cast<libIRDB::Instruction_t*>(first);
+	assert(real_first);
+        real_first->GetRelocations().clear();
+	first->setIBTargets(NULL);
+	//Note that the instruction just inserted should have the same exception handling
+	//info as the instructions immediately around it.
+	//Thus the exception handling information (EhCallSite and EhProgram) are kept the 
+	//same from the copy of first (unlike with relocations and IBT's).
+
+	virp->changeRegistryKey(first,next);
+        setInstructionsDetails(virp,first,dataBits,next,target);
+
+        return next;
+}
+
+Instruction_t* IRDB_SDK::insertAssemblyAfter(FileIR_t* virp, Instruction_t* first, string assembly, Instruction_t *target)
+{
+	Instruction_t *new_instr = allocateNewInstruction(virp,first);
+	IRDB_SDK::setInstructionAssembly(virp,new_instr,assembly,first->getFallthrough(), target);
+        first->setFallthrough(new_instr);
+        return new_instr;
+}
+
+#if 0
+Instruction_t* insertAssemblyAfter(FileIR_t* virp, Instruction_t* first, string assembly)
+{
+        return insertAssemblyAfter(virp,first,assembly,NULL);
+
+}
+#endif
+
+Instruction_t* IRDB_SDK::insertDataBitsAfter(FileIR_t* virp, Instruction_t* first, string dataBits, Instruction_t *target)
+{
+	Instruction_t *new_instr = allocateNewInstruction(virp,first);
+        setInstructionsDetails(virp,new_instr,dataBits,first->getFallthrough(), target);
+        first->setFallthrough(new_instr);
+
+        return new_instr;
+}
+
+#if 0
+Instruction_t* insertDataBitsAfter(FileIR_t* virp, Instruction_t* first, string dataBits)
+{
+        return insertDataBitsAfter(virp,first,dataBits,NULL);
+}
+#endif
+
+Instruction_t* IRDB_SDK::addNewDataBits(FileIR_t* firp, Instruction_t *p_instr, string p_bits)
+{
+	Instruction_t* newinstr;
+        if (p_instr)
+                newinstr = allocateNewInstruction(firp,p_instr->getAddress()->getFileID(), p_instr->getFunction());
+        else
+                newinstr = allocateNewInstruction(firp,firp->getFile()->getFileID(), NULL);
+
+        newinstr->setDataBits(p_bits);
+
+        if (p_instr)
+        {
+                newinstr->setFallthrough(p_instr->getFallthrough());
+                p_instr->setFallthrough(newinstr);
+        }
+
+        return newinstr;
+}
+
+Instruction_t* IRDB_SDK::addNewDataBits(FileIR_t* firp, string p_bits)
+{
+	return IRDB_SDK::addNewDataBits(firp,nullptr,p_bits);
+}
+
+
+Instruction_t* IRDB_SDK::addNewAssembly(FileIR_t* firp, Instruction_t *p_instr, string p_asm)
+{
+	Instruction_t* newinstr;
+        if (p_instr)
+                newinstr = allocateNewInstruction(firp,p_instr->getAddress()->getFileID(), p_instr->getFunction());
+        else
+                newinstr = allocateNewInstruction(firp,firp->getFile()->getFileID(), NULL);
+
+        firp->registerAssembly(newinstr, p_asm);
+
+        if (p_instr)
+        {
+                newinstr->setFallthrough(p_instr->getFallthrough());
+                p_instr->setFallthrough(newinstr);
+        }
+
+        return newinstr;
+}
+
+Instruction_t* IRDB_SDK::addNewAssembly(FileIR_t* firp, string p_asm)
+{
+	return IRDB_SDK::addNewAssembly(firp,nullptr,p_asm);
+}
+
+
+//Does not insert into any variant
+Instruction_t* copyInstruction(Instruction_t* instr)
+{
+	Instruction_t* cpy = new libIRDB::Instruction_t();
+
+	copyInstruction(instr,cpy);
+
+	return cpy;
+}
+
+Instruction_t* copyInstruction(FileIR_t* virp, Instruction_t* instr)
+{
+	Instruction_t* cpy = allocateNewInstruction(virp,instr);
+
+	copyInstruction(instr,cpy);
+
+	return cpy;
+}
+
+void copyInstruction(Instruction_t* src, Instruction_t* dest)
+{
+	auto real_dest=dynamic_cast<libIRDB::Instruction_t*>(dest);
+	dest->setDataBits(src->getDataBits());
+	dest->setComment(src->getComment());
+	dest->setCallback(src->getCallback());
+	dest->setFallthrough(src->getFallthrough());
+	dest->setTarget(src->getTarget());
+        dest->setIBTargets(src->getIBTargets()); 
+	real_dest->GetRelocations()=src->getRelocations();
+        dest->setEhProgram(src->getEhProgram());
+	dest->setEhCallSite(src->getEhCallSite());
+}
+
+Instruction_t* allocateNewInstruction(FileIR_t* virp, DatabaseID_t p_fileID,Function_t* func)
+{
+	auto instr = new libIRDB::Instruction_t();
+	auto a     = new libIRDB::AddressID_t();
+
+	a->setFileID(p_fileID);
+
+	instr->setFunction(func);
+	instr->setAddress(a);
+	if(func)
+	{
+		auto real_func=dynamic_cast<libIRDB::Function_t*>(func);
+		assert(func);
+		real_func->GetInstructions().insert(instr);
+	}
+
+	auto real_virp=dynamic_cast<libIRDB::FileIR_t*>(virp);
+	assert(real_virp);
+	real_virp->GetInstructions().insert(instr);
+	real_virp->GetAddresses().insert(a);
+
+//	inserted_instr[func].insert(instr);
+//	inserted_addr[func].insert(a);
+	
+	return instr;
+}
+
+Instruction_t* allocateNewInstruction(FileIR_t* virp, Instruction_t *template_instr)
+{
+	Function_t *func = template_instr->getFunction();
+	DatabaseID_t fileID = template_instr->getAddress()->getFileID();
+	return allocateNewInstruction(virp, fileID, func);
+}
+
+void IRDB_SDK::setInstructionAssembly(FileIR_t* virp,Instruction_t *p_instr, const string& p_assembly, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	if (p_instr == NULL) return;
+	
+	///TODO: what if bad assembly?
+	virp->registerAssembly(p_instr,p_assembly);
+	p_instr->setComment(p_assembly); 
+	p_instr->setFallthrough(p_fallThrough); 
+	p_instr->setTarget(p_target); 
+
+	auto real_virp=dynamic_cast<libIRDB::FileIR_t*>(virp);
+	assert(real_virp);
+	real_virp->GetAddresses().insert(p_instr->getAddress());
+	real_virp->GetInstructions().insert(p_instr);
+}
+
+void IRDB_SDK::setInstructionAssembly(FileIR_t* virp,Instruction_t *p_instr, const string& p_assembly)
+{
+	IRDB_SDK::setInstructionAssembly(virp,p_instr,p_assembly, p_instr->getFallthrough(), p_instr->getTarget());
+}
+
+
diff --git a/irdb-lib/libIRDB-transform/src/transform.cpp b/irdb-lib/libIRDB-transform/src/transform.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..fb70acbcdd23e41ad6abf9b94c90eb4997d289fa
--- /dev/null
+++ b/irdb-lib/libIRDB-transform/src/transform.cpp
@@ -0,0 +1,1590 @@
+/*
+ * Copyright (c) 2013, 2014 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <irdb-transform>
+
+using namespace IRDB_SDK;
+
+Transform::Transform(FileIR_t *p_fileIR)
+	:
+	m_fileIR (p_fileIR) 
+{
+	assert(m_fileIR);
+}
+
+FileIR_t* Transform::getFileIR() 
+{ 
+	return m_fileIR; 
+}
+
+const FileIR_t* Transform::getFileIR() const
+{ 
+	return m_fileIR; 
+}
+
+Instruction_t* Transform::insertAssemblyBefore(Instruction_t* before, const string &the_asm, Instruction_t* target)
+{
+	return IRDB_SDK::insertAssemblyBefore(getFileIR(), before, the_asm, target);
+}
+
+
+Instruction_t* Transform::insertAssemblyAfter(Instruction_t* before, const string &the_asm, Instruction_t* target)
+{
+	return IRDB_SDK::insertAssemblyAfter(getFileIR(), before, the_asm, target);
+}
+
+Instruction_t* Transform::insertDataBitsBefore(Instruction_t* before, const string &the_asm, Instruction_t* target)
+{
+	return IRDB_SDK::insertDataBitsBefore(getFileIR(), before, the_asm, target);
+}
+
+Instruction_t* Transform::insertDataBitsAfter(Instruction_t* before, const string &the_asm, Instruction_t* target)
+{
+	return IRDB_SDK::insertDataBitsAfter(getFileIR(), before, the_asm, target);
+}
+
+Instruction_t* Transform::addNewDataBits(const string& p_bits)
+{
+	return IRDB_SDK::addNewDataBits(getFileIR(), p_bits);
+}
+
+Instruction_t* Transform::addNewAssembly(const string& p_bits)
+{
+	return IRDB_SDK::addNewAssembly(getFileIR(), p_bits);
+}
+
+void Transform::setInstructionAssembly(Instruction_t* instr, const string& p_asm, Instruction_t *p_new_fallthrough, Instruction_t* p_new_target)
+{
+	return IRDB_SDK::setInstructionAssembly(getFileIR(), instr, p_asm, p_new_fallthrough, p_new_target);
+}
+
+void Transform::setInstructionAssembly(Instruction_t* instr, const string& p_asm)
+{
+	return IRDB_SDK::setInstructionAssembly(getFileIR(), instr, p_asm);
+}
+
+
+
+#if 0
+void Transform::addInstruction(Instruction_t *p_instr, string p_dataBits, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	if (p_instr == NULL) return;
+
+	p_instr->setDataBits(p_dataBits);
+	p_instr->setComment(p_instr->getDisassembly());
+	p_instr->setFallthrough(p_fallThrough); 
+	p_instr->setTarget(p_target); 
+	m_fileIR->GetAddresses().insert(p_instr->getAddress());
+	m_fileIR->GetInstructions().insert(p_instr);
+}
+
+#define BENSWAY
+
+//
+//  Before:                              After:
+//  <p_instrumented> ["mov edx,1"]       <p_newInstr> []
+//                                       <dupInstr>   ["mov edx,1"] <-- returns
+//
+Instruction_t* Transform::carefullyInsertBefore(Instruction_t* &p_instrumented, Instruction_t * &p_newInstr)
+{
+
+//For all insertBefore functions:
+//The "first" instruction will have its contents replaced and a duplicate of "first" will be in the follow of first. 
+//This duplicate is returned since the user already has a pointer to first.
+//To insert before an instruction is the same as modifying the original instruction, and inserting after it
+//a copy of the original instruction 
+
+#ifdef BENSWAY
+	Instruction_t* i2 = IRDBUtility::insertAssemblyBefore(m_fileIR, p_instrumented, m_fileIR->lookupAssembly(p_newInstr), p_newInstr->getTarget());
+cerr << "carefullyInsertBefore (Ben's Way): @: 0x" << std::hex << p_instrumented->getAddress() << std::dec << " old instruction: " << p_instrumented->getDisassembly() << " new instruction: " << m_fileIR->lookupAssembly(p_newInstr) << endl;
+	return i2;
+#else
+	DatabaseID_t fileID = p_instrumented->getAddress()->getFileID();
+	Function_t* func = p_instrumented->getFunction();
+
+	assert(p_instrumented && p_newInstr && p_instrumented->getAddress());
+
+// why is old instrunction blank?
+cerr << "(1) carefullyInsertBefore: @: 0x" << std::hex << p_instrumented->getAddress() << std::dec << " old instruction: " << p_instrumented->getDisassembly() << " new instruction: " << m_fileIR->lookupAssembly(p_newInstr) << endl;
+
+	// duplicate old instrumented instruction
+	Instruction_t* dupInstr = allocateNewInstruction(fileID, func);
+
+	dupInstr->setDataBits(p_instrumented->GetDataBits());
+	dupInstr->setComment(p_instrumented->getComment());
+	dupInstr->setCallback(p_instrumented->getCallback());
+	dupInstr->setFallthrough(p_instrumented->getFallthrough());
+	dupInstr->setTarget(p_instrumented->getTarget());
+	dupInstr->setOriginalAddressID(p_instrumented->getOriginalAddressID());
+	AddressID_t *saveIBTA = p_instrumented->GetIndirectBranchTargetAddress();
+	dupInstr->setIndirectBranchTargetAddress(NULL);
+
+	//
+	//  pre: p_instrument --> "mov edx, 1"
+	//	
+	// post: p_instrument no longer in map
+	//       new --> "mov edx, 1"
+	//
+	// this function is equivalent to:
+	//      m_fileIR->UnregisterAssembly(p_instrumented);
+	//      m_fileIR->registerAssembly(dupInstr, newAssemblyCode);
+	//
+	m_fileIR->ChangeRegistryKey(p_instrumented, dupInstr);
+
+	if (p_newInstr->GetDataBits().size() == 0)
+		m_fileIR->registerAssembly(p_instrumented, m_fileIR->lookupAssembly(p_newInstr));
+	else
+		p_instrumented->setDataBits(p_newInstr->GetDataBits()); 
+
+	p_instrumented->setComment(p_newInstr->getComment());
+	p_instrumented->setCallback(p_newInstr->getCallback());
+	p_instrumented->setFallthrough(dupInstr);
+
+	p_instrumented->setOriginalAddressID(BaseObj_t::NOT_IN_DATABASE);
+	p_instrumented->setIndirectBranchTargetAddress(saveIBTA);
+	p_instrumented->GetRelocations().clear();
+
+   	p_newInstr = p_instrumented;
+
+cerr << "(2) carefullyInsertBefore: @: 0x" << std::hex << p_instrumented->getAddress() << std::dec << " old instruction: " << dupInstr->getDisassembly() << " new instruction: " << m_fileIR->lookupAssembly(p_newInstr) << endl;
+	return dupInstr;
+#endif
+}
+
+
+void Transform::addPushf(Instruction_t *p_pushf_i, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+	dataBits[0] = 0x9c;
+	addInstruction(p_pushf_i, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addPushRegister(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+
+	if (p_reg == rn_EAX || p_reg == rn_RAX)
+	{
+		dataBits[0] = 0x50; 
+	} 
+	else if (p_reg == rn_EBX || p_reg == rn_RBX)
+	{
+		dataBits[0] = 0x53; 
+	} 
+	else if (p_reg == rn_ECX || p_reg == rn_RCX)
+	{
+		dataBits[0] = 0x51; 
+	}
+	else if (p_reg == rn_EDX || p_reg == rn_RDX)
+	{
+		dataBits[0] = 0x52; 
+	}
+	else if (p_reg == rn_ESI || p_reg == rn_RSI)
+	{
+		dataBits[0] = 0x56; 
+	}
+	else if (p_reg == rn_EDI || p_reg == rn_RDI)
+	{
+		dataBits[0] = 0x57; 
+	}
+	else if (p_reg == rn_EBP || p_reg == rn_RBP)
+	{
+		dataBits[0] = 0x55; 
+	}
+	else if (p_reg == rn_ESP || p_reg == rn_RSP)
+	{
+		dataBits[0] = 0x54; 
+	}
+	else
+	{
+		dataBits.resize(2);
+		dataBits[0] = 0x41;
+		if (p_reg == rn_R8)
+		{
+			dataBits[1] = 0x50;
+		} 
+		else if (p_reg == rn_R9)
+		{
+			dataBits[1] = 0x51;
+		} 
+		else if (p_reg == rn_R10)
+		{
+			dataBits[1] = 0x52;
+		} 
+		else if (p_reg == rn_R11)
+		{
+			dataBits[1] = 0x53;
+		} 
+		else if (p_reg == rn_R12)
+		{
+			dataBits[1] = 0x54;
+		} 
+		else if (p_reg == rn_R13)
+		{
+			dataBits[1] = 0x55;
+		} 
+		else if (p_reg == rn_R14)
+		{
+			dataBits[1] = 0x56;
+		} 
+		else if (p_reg == rn_R15)
+		{
+			dataBits[1] = 0x57;
+		}
+		else
+		{
+			cerr << "Transform::addPushRegister: unhandled register: " << p_reg << endl;
+			assert(0);
+			return;
+		}
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addPopRegister(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+
+	if (p_reg == rn_EAX || p_reg == rn_RAX)
+	{
+		dataBits[0] = 0x58; 
+	} 
+	else if (p_reg == rn_EBX || p_reg == rn_RBX)
+	{
+		dataBits[0] = 0x5b; 
+	} 
+	else if (p_reg == rn_ECX || p_reg == rn_RCX)
+	{
+		dataBits[0] = 0x59; 
+	}
+	else if (p_reg == rn_EDX || p_reg == rn_RDX)
+	{
+		dataBits[0] = 0x5a; 
+	}
+	else if (p_reg == rn_ESI || p_reg == rn_RSI)
+	{
+		dataBits[0] = 0x5e; 
+	}
+	else if (p_reg == rn_EDI || p_reg == rn_RDI)
+	{
+		dataBits[0] = 0x5f; 
+	}
+	else if (p_reg == rn_EBP || p_reg == rn_RBP)
+	{
+		dataBits[0] = 0x5d; 
+	}
+	else if (p_reg == rn_ESP || p_reg == rn_RSP)
+	{
+		dataBits[0] = 0x5c; 
+	}
+	else
+	{
+		dataBits.resize(2);
+		dataBits[0] = 0x41;
+		if (p_reg == rn_R8)
+		{
+			dataBits[1] = 0x58;
+		} 
+		else if (p_reg == rn_R9)
+		{
+			dataBits[1] = 0x59;
+		} 
+		else if (p_reg == rn_R10)
+		{
+			dataBits[1] = 0x5a;
+		} 
+		else if (p_reg == rn_R11)
+		{
+			dataBits[1] = 0x5b;
+		} 
+		else if (p_reg == rn_R12)
+		{
+			dataBits[1] = 0x5c;
+		} 
+		else if (p_reg == rn_R13)
+		{
+			dataBits[1] = 0x5d;
+		} 
+		else if (p_reg == rn_R14)
+		{
+			dataBits[1] = 0x5e;
+		} 
+		else if (p_reg == rn_R15)
+		{
+			dataBits[1] = 0x5f;
+		}
+		else
+		{
+			cerr << "Transform::addPopRegister: unhandled register";
+			assert(0);
+			return;
+		}
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addPusha(Instruction_t *p_pusha_i, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+	dataBits[0] = 0x60;
+	addInstruction(p_pusha_i, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addPopf(Instruction_t *p_popf_i, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+	dataBits[0] = 0x9d;
+	addInstruction(p_popf_i, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addPopa(Instruction_t *p_popa_i, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+	dataBits[0] = 0x61;
+	addInstruction(p_popa_i, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addNop(Instruction_t *p_nop_i, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(1);
+	dataBits[0] = 0x90;
+	p_nop_i->setComment(string("NOP"));
+	addInstruction(p_nop_i, dataBits, p_fallThrough, NULL);
+}
+
+Instruction_t* Transform::allocateNewInstruction(DatabaseID_t p_fileID, Function_t* p_func)
+{
+	Instruction_t *instr = new libIRDB::Instruction_t();
+	AddressID_t *a = new libIRDB::AddressID_t();
+
+	a->setFileID(p_fileID);
+
+	instr->setFunction(p_func);
+	instr->setAddress(a);
+
+	m_fileIR->GetInstructions().insert(instr);
+	m_fileIR->GetAddresses().insert(a);
+	return instr;
+}
+
+VirtualOffset_t Transform::getAvailableAddress()
+{
+/*
+	// traverse all instructions
+	// grab address
+
+	// @todo: lookup instruction size so that we don't waste any space
+	// for some reason the max available address is incorrect! was ist los?
+
+	VirtualOffset_t availableAddressOffset = 0;
+	for(
+		set<Instruction_t*>::const_iterator it=p_virp->GetInstructions().begin();
+		it!=p_virp->GetInstructions().end(); 
+		++it
+	   )
+	{
+		Instruction_t* insn=*it;
+		if (!insn) continue;
+
+		AddressID_t* addr = insn->getAddress();
+		VirtualOffset_t offset = addr->setVirtualOffset();
+                
+		if (offset > availableAddressOffset)
+		{
+			availableAddressOffset = offset;
+		}
+	}
+// availableAddressOffset + 16;
+*/
+
+	static int counter = -16;
+	counter += 16;
+	return 0xf0000000 + counter;
+}
+
+void Transform::addCallbackHandler(string p_detector, Instruction_t *p_instrumentedInstruction, Instruction_t *p_instruction, Instruction_t *p_fallThrough, int p_policy, AddressID_t *p_addressOriginalInstruction)
+{
+
+	assert(getFileIR() && p_instruction && p_fallThrough);
+
+	string dataBits;
+
+	DatabaseID_t fileID = p_instruction->getAddress()->getFileID();
+	Function_t* func = p_instruction->getFunction();
+
+ 	// create and register new instructions (and addresses)
+	Instruction_t* pushf_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pusha_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pushPolicy_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pusharg_i = allocateNewInstruction(fileID, func);
+	Instruction_t* pushret_i = allocateNewInstruction(fileID, func);
+	Instruction_t* poparg_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popPolicy_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popa_i = allocateNewInstruction(fileID, func);
+	Instruction_t* popf_i = allocateNewInstruction(fileID, func);
+
+	// pin the poparg instruction 
+	VirtualOffset_t postDetectorReturn = getAvailableAddress();
+	poparg_i->getAddress()->setVirtualOffset(postDetectorReturn);
+
+	// link callback handler sequence to instrumented instruction
+	p_instruction->setFallthrough(pushf_i);
+	p_instruction->setComment(p_instruction->getComment() + " -- start of callback handler sequence");
+
+	// pushf   
+	addPushf(pushf_i, pusha_i);
+
+	// pusha   
+	addPusha(pusha_i, pushPolicy_i);
+
+	// push detector exit policy
+	//     0 - default
+	//     1 - continue
+	//     2 - exit
+	//     3 - saturating arithmetic
+	dataBits.resize(5);
+	dataBits[0] = 0x68;
+	int *tmpi = (int *) &dataBits[1];
+	*tmpi = p_policy;
+	pushPolicy_i->setDataBits(dataBits);
+	pushPolicy_i->setComment(pushPolicy_i->getDisassembly() + string(" - policy spec"));
+	pushPolicy_i->setFallthrough(pusharg_i); 
+
+	// push (PC of instrumented instruction)
+	dataBits.resize(5);
+	dataBits[0] = 0x68;
+	VirtualOffset_t *tmp = (VirtualOffset_t *) &dataBits[1];
+	if (p_addressOriginalInstruction)
+		*tmp = p_addressOriginalInstruction->getVirtualOffset();
+	else
+		*tmp = p_instrumentedInstruction->getAddress()->getVirtualOffset();
+	pusharg_i->setDataBits(dataBits);
+	pusharg_i->setComment(pusharg_i->getDisassembly());
+	pusharg_i->setFallthrough(pushret_i); 
+
+	// pushret   
+	dataBits.resize(5);
+	dataBits[0] = 0x68;
+	tmp = (VirtualOffset_t *) &dataBits[1];
+	*tmp = postDetectorReturn;
+	pushret_i->setDataBits(dataBits);
+	pushret_i->setComment(pushret_i->getDisassembly());
+	pushret_i->setFallthrough(poparg_i); 
+
+	// poparg
+	dataBits.resize(1);
+	dataBits[0] = 0x58;
+	poparg_i->setDataBits(dataBits);
+	poparg_i->setComment(poparg_i->getDisassembly() + " -- with callback to " + p_detector + " orig: " + p_instruction->getComment()) ;
+	poparg_i->setFallthrough(popPolicy_i); 
+	poparg_i->setCallback(p_detector); 
+	auto poparg_i_indTarg =new libIRDB::AddressID_t();
+	m_fileIR->GetAddresses().insert(poparg_i_indTarg);
+	poparg_i_indTarg->setVirtualOffset(poparg_i->getAddress()->getVirtualOffset());
+	poparg_i_indTarg->setFileID(BaseObj_t::NOT_IN_DATABASE);
+	poparg_i->setIndirectBranchTargetAddress(poparg_i_indTarg);
+
+	// popPolicy
+	dataBits.resize(1);
+	dataBits[0] = 0x58;
+	popPolicy_i->setDataBits(dataBits);
+	popPolicy_i->setFallthrough(popa_i); 
+
+	// popa   
+	addPopa(popa_i, popf_i);
+
+	// popf   
+	addPopf(popf_i, p_fallThrough);
+}
+
+
+#if 0
+// returns true if BeaEngine says arg1 of the instruction is a register 
+bool Transform::hasTargetRegister(Instruction_t *p_instruction, int p_argNo)
+{
+	if (!p_instruction)
+		return false;
+
+	DISASM disasm;
+	Disassemble(p_instruction,disasm);
+	
+	if (p_argNo == 1)
+		return disasm.Argument1.ArgType & 0xFFFF0000 & REGISTER_TYPE;
+	else if (p_argNo == 2)
+		return disasm.Argument2.ArgType & 0xFFFF0000 & REGISTER_TYPE;
+	else if (p_argNo == 3)
+		return disasm.Argument3.ArgType & 0xFFFF0000 & REGISTER_TYPE;
+	else
+		return false;
+}
+
+
+RegisterName Transform::getTargetRegister(Instruction_t *p_instruction, int p_argNo)
+{
+	if (hasTargetRegister(p_instruction, p_argNo))
+	{
+		DISASM disasm;
+		Disassemble(p_instruction,disasm);
+
+		if (p_argNo == 1)
+			return Register::getRegister(disasm.Argument1.ArgMnemonic);
+		else if (p_argNo == 2)
+			return Register::getRegister(disasm.Argument2.ArgMnemonic);
+		else if (p_argNo == 3)
+			return Register::getRegister(disasm.Argument3.ArgMnemonic);
+	}
+	else
+		return rn_UNKNOWN;
+}
+
+//
+// Returns true iff instruction is MUL (according to BeaEngine)
+//
+bool Transform::isMultiplyInstruction(Instruction_t *p_instruction)
+{
+	if (!p_instruction)
+		return false;
+
+	std::string assembly = m_fileIR->lookupAssembly(p_instruction);
+	if (assembly.length() > 0)
+	{
+		return my_strcasestr(assembly.c_str(), "MUL") != NULL;
+	}
+
+	DISASM disasm;
+	Disassemble(p_instruction,disasm);
+
+	// beaengine adds space at the end of the mnemonic string
+	return my_strcasestr(disasm.Instruction.Mnemonic, "MUL ") != NULL;
+}
+
+
+//
+// Returns true iff instruction is a MOV (according to BeaEngine)
+//
+bool Transform::isMovInstruction(Instruction_t *p_instruction)
+{
+	if (!p_instruction)
+		return false;
+
+	std::string assembly = m_fileIR->lookupAssembly(p_instruction);
+	if (assembly.length() > 0)
+	{
+		return my_strcasestr(assembly.c_str(), "MOV") != NULL;
+	}
+
+	DISASM disasm;
+	Disassemble(p_instruction,disasm);
+
+	// nb: beaengine adds space at the end of the mnemonic string
+	return my_strcasestr(disasm.Instruction.Mnemonic, "MOV") != NULL;
+}
+
+//
+// Returns true iff instruction is ADD or SUB (according to BeaEngine)
+//
+bool Transform::isAddSubNonEspInstruction(Instruction_t *p_instruction)
+{
+	if (!p_instruction)
+		return false;
+
+	DISASM disasm;
+	Disassemble(p_instruction,disasm);
+
+	// beaengine adds space at the end of the mnemonic string
+	if (my_strcasestr(disasm.Instruction.Mnemonic, "ADD "))
+	{
+		return true;
+	}
+	else if (my_strcasestr(disasm.Instruction.Mnemonic, "SUB ")) 
+	{
+		if (my_strcasestr(disasm.Argument1.ArgMnemonic,"esp") &&
+			(disasm.Argument2.ArgType & 0xFFFF0000 & (CONSTANT_TYPE | ABSOLUTE_)))
+		{
+			// optimization: filter out "sub esp, K"
+			return false;
+		}
+		return true;
+	}
+
+	return false;
+}
+#endif
+
+void Transform::addTestRegister8(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(2);
+	if (p_reg == rn_AL)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xc0;
+	}
+	else if (p_reg == rn_BL)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xdb;
+	}
+	else if (p_reg == rn_CL)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xc9;
+	}
+	else if (p_reg == rn_DL)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xd2;
+	}
+	else if (p_reg == rn_AH)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xe4;
+	}
+	else if (p_reg == rn_BH)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xff;
+	}
+	else if (p_reg == rn_CH)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xed;
+	}
+	else if (p_reg == rn_DH)
+	{
+		dataBits[0] = 0x84;
+		dataBits[1] = 0xf6;
+	}
+	else
+	{
+		cerr << "Transform::addTestRegister8(): unhandled register" << endl;
+		assert(0);
+		return;
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addTestRegister16(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(3);
+	if (p_reg == rn_AX)
+	{
+		dataBits[0] = 0x66;
+		dataBits[1] = 0x85;
+		dataBits[2] = 0xc0;
+	}
+	else if (p_reg == rn_BX)
+	{
+		dataBits[0] = 0x66;
+		dataBits[1] = 0x85;
+		dataBits[2] = 0xdb;
+	}
+	else if (p_reg == rn_CX)
+	{
+		dataBits[0] = 0x66;
+		dataBits[1] = 0x85;
+		dataBits[2] = 0xc9;
+	}
+	else if (p_reg == rn_DX)
+	{
+		dataBits[0] = 0x66;
+		dataBits[1] = 0x85;
+		dataBits[2] = 0xd2;
+	}
+	else if (p_reg == rn_BP)
+	{
+		assert(0);
+	}
+	else if (p_reg == rn_SP)
+	{
+		assert(0);
+	}
+	else if (p_reg == rn_SI)
+	{
+		assert(0);
+	}
+	else if (p_reg == rn_DI)
+	{
+		assert(0);
+	}
+	else
+	{
+		cerr << "Transform::addTestRegister16(): unhandled register" << endl;
+		assert(0);
+		return;
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+// test <reg32>, <reg32>
+void Transform::addTestRegister32(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(2);
+	if (p_reg == rn_EAX)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xc0;
+	}
+	else if (p_reg == rn_EBX)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xdb;
+	}
+	else if (p_reg == rn_ECX)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xc9;
+	}
+	else if (p_reg == rn_EDX)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xd2;
+	}
+	else if (p_reg == rn_ESI)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xf6;
+	}
+	else if (p_reg == rn_EDI)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xff;
+	}
+	else if (p_reg == rn_EBP)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xed;
+	}
+	else if (p_reg == rn_ESP)
+	{
+		dataBits[0] = 0x85;
+		dataBits[1] = 0xe4;
+	}
+	else
+	{
+		cerr << "Transform::addTestRegister32(): unhandled register" << endl;
+		assert(0);
+		return;
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+
+void Transform::addTestRegister(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	if (Register::is8bit(p_reg))
+		addTestRegister8(p_instr, p_reg, p_fallThrough);
+	else if (Register::is16bit(p_reg))
+		addTestRegister16(p_instr, p_reg, p_fallThrough);
+	else if (Register::is32bit(p_reg))
+		addTestRegister32(p_instr, p_reg, p_fallThrough);
+}
+
+void Transform::addTestRegisterMask(Instruction_t *p_instr, RegisterName p_reg, unsigned p_mask, Instruction_t *p_fallThrough)
+{
+	if (Register::is32bit(p_reg))
+		addTestRegisterMask32(p_instr, p_reg, p_mask, p_fallThrough);
+}
+
+void Transform::addTestRegisterMask32(Instruction_t *p_instr, RegisterName p_reg, unsigned p_mask, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(6); // all but EAX take 6 bytes
+	unsigned *tmp;
+
+	if (p_reg == rn_EAX)
+	{
+		dataBits.resize(5);
+		dataBits[0] = 0xa9;
+		tmp = (unsigned *) &dataBits[1];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_EBX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc3;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_ECX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc1;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_EDX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc2;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_ESI)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc6;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_EDI)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc7;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_EBP)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc5;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else if (p_reg == rn_ESP)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xc4;
+		tmp = (unsigned *) &dataBits[2];
+		*tmp = p_mask;
+	}
+	else
+	{
+		cerr << "Transform::addTestRegisterMask32(): unhandled register: " << p_reg << endl;
+		assert(0);
+		return;
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+void Transform::addCmpRegisterMask(Instruction_t *p_instr, RegisterName p_reg, unsigned p_mask, Instruction_t *p_fallThrough)
+{
+	if (Register::is32bit(p_reg))
+		addCmpRegisterMask32(p_instr, p_reg, p_mask, p_fallThrough);
+}
+
+void Transform::addCmpRegisterMask32(Instruction_t *p_instr, RegisterName p_reg, unsigned p_mask, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	unsigned *tmp;
+
+	if (p_reg == rn_EAX)
+	{
+      dataBits.resize(5); // EAX gets compact encoding
+		dataBits[0] = 0x3d;
+		tmp = (unsigned *) &dataBits[1];
+		*tmp = p_mask;
+	}
+	else 
+   { // common code for non-EAX cases first
+	  dataBits.resize(6); // all but EAX take 6 bytes
+     dataBits[0] = 0x81;
+     tmp = (unsigned *) &dataBits[2];
+     *tmp = p_mask;
+     if (p_reg == rn_EBX)
+	  {
+       dataBits[1] = 0xfb;
+     }
+     else if (p_reg == rn_ECX)
+     {
+       dataBits[1] = 0xf9;
+     }
+     else if (p_reg == rn_EDX)
+     {
+       dataBits[1] = 0xfa;
+     }
+     else if (p_reg == rn_EBP)
+     {
+       dataBits[1] = 0xfd;
+     }
+     else if (p_reg == rn_ESI)
+     {
+       dataBits[1] = 0xfe;
+     }
+     else if (p_reg == rn_EDI)
+     {
+       dataBits[1] = 0xff;
+     }
+     else
+     {
+       cerr << "Transform::addCmpRegisterMask32(): unhandled register" << endl;
+		assert(0);
+       return;
+     }
+   }
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+// jns - jump not signed
+void Transform::addJns(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string dataBits;
+	dataBits.resize(2);
+	dataBits[0] = 0x79;
+	dataBits[1] = 0x00; // value doesn't matter -- we will fill it in later
+	addInstruction(p_instr, dataBits, p_fallThrough, p_target);
+}
+
+// jz - jump zero (same as je - jump if equal)
+void Transform::addJz(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string dataBits;
+	dataBits.resize(2);
+	dataBits[0] = 0x74;
+	dataBits[1] = 0x00; // value doesn't matter -- we will fill it in later
+
+	addInstruction(p_instr, dataBits, p_fallThrough, p_target);
+}
+
+// jnz - jump not zero (same as jne - jump if not equal)
+void Transform::addJnz(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string dataBits;
+	dataBits.resize(2);
+	dataBits[0] = 0x75;
+	dataBits[1] = 0x00; // value doesn't matter -- we will fill it in later
+
+	addInstruction(p_instr, dataBits, p_fallThrough, p_target);
+}
+
+// jae - jump if above or equal (unsigned) (same as jnb and jnc)
+void Transform::addJae(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string dataBits;
+	dataBits.resize(2);
+	dataBits[0] = 0x73;
+	dataBits[1] = 0x00; // value doesn't matter -- we will fill it in later
+
+	addInstruction(p_instr, dataBits, p_fallThrough, p_target);
+}
+
+// jo - jump overflow
+void Transform::addJo(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string dataBits;
+	dataBits.resize(2);
+	dataBits[0] = 0x70;
+	dataBits[1] = 0x00; // value doesn't matter -- we will fill it in later
+
+	addInstruction(p_instr, dataBits, p_fallThrough, p_target);
+}
+// jc - jump carry
+void Transform::addJc(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string dataBits;
+	dataBits.resize(2);
+	dataBits[0] = 0x72;
+	dataBits[1] = 0x00; // value doesn't matter -- we will fill it in later
+
+	addInstruction(p_instr, dataBits, p_fallThrough, p_target);
+}
+
+// not <reg> -- negate register
+void Transform::addNot(Instruction_t *p_instr, RegisterName p_reg, Instruction_t *p_fallThrough)
+{
+	string dataBits;
+	dataBits.resize(2); 
+
+	if (p_reg == rn_EAX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xd0;
+	}
+	else if (p_reg == rn_EBX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xd3;
+	}
+	else if (p_reg == rn_ECX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xd1;
+	}
+	else if (p_reg == rn_EDX)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xd2;
+	}
+	else if (p_reg == rn_ESI)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xd6;
+	}
+	else if (p_reg == rn_EDI)
+	{
+		dataBits[0] = 0xf7;
+		dataBits[1] = 0xd7;
+	}
+	else if (p_reg == rn_AX)
+	{
+		dataBits.resize(3); 
+		dataBits[0] = 0x66;
+		dataBits[1] = 0xf7;
+		dataBits[2] = 0xd0;
+	}
+	else if (p_reg == rn_BX)
+	{
+		dataBits.resize(3); 
+		dataBits[0] = 0x66;
+		dataBits[1] = 0xf7;
+		dataBits[2] = 0xd3;
+	}
+	else if (p_reg == rn_CX)
+	{
+		dataBits.resize(3); 
+		dataBits[0] = 0x66;
+		dataBits[1] = 0xf7;
+		dataBits[2] = 0xd1;
+	}
+	else if (p_reg == rn_DX)
+	{
+		dataBits.resize(3); 
+		dataBits[0] = 0x66;
+		dataBits[1] = 0xf7;
+		dataBits[2] = 0xd2;
+	}
+	else if (p_reg == rn_AL)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd0;
+	}
+	else if (p_reg == rn_BL)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd3;
+	}
+	else if (p_reg == rn_CL)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd1;
+	}
+	else if (p_reg == rn_DL)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd2;
+	}
+	else if (p_reg == rn_AH)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd4;
+	}
+	else if (p_reg == rn_BH)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd7;
+	}
+	else if (p_reg == rn_CH)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd5;
+	}
+	else if (p_reg == rn_DH)
+	{
+		dataBits[0] = 0xf6;
+		dataBits[1] = 0xd6;
+	}
+
+	else
+	{
+		cerr << "Transform::addNot(): unhandled register" << endl;
+		assert(0);
+		return;
+	}
+
+	addInstruction(p_instr, dataBits, p_fallThrough, NULL);
+}
+
+// add r1, r2
+void Transform::addAddRegisters(Instruction_t *p_instr, RegisterName p_regTgt, RegisterName p_regSrc, Instruction_t *p_fallThrough)
+{
+	// too many combinations, just use the assembler
+	string assembly = "add " + Register::toString(p_regTgt) + ", " + Register::toString(p_regSrc);
+#ifdef OPTIMIZE_ASSEMBLY
+	m_fileIR->registerAssembly(p_instr, assembly);
+#else
+	if (!p_instr->assemble(assembly))
+	{
+		cerr << "addAddRegisters(): error in assembling instruction: " << assembly << endl;
+		assert(0);
+		return;
+	}
+#endif
+
+	p_instr->setFallthrough(p_fallThrough);
+}
+
+// add r1, constant
+void Transform::addAddRegisterConstant(Instruction_t *p_instr, RegisterName p_reg, int p_constantValue, Instruction_t *p_fallThrough)
+{
+	// too many combinations, just use the assembler
+	char buf[256];
+	sprintf(buf, "add %s, %d", Register::toString(p_reg).c_str(), p_constantValue);
+	string assembly(buf);
+#ifdef OPTIMIZE_ASSEMBLY
+	m_fileIR->registerAssembly(p_instr, assembly);
+#else
+	if (!p_instr->assemble(assembly))
+	{
+		cerr << "Transform::addAddConstant(): error in assembling instruction: " << assembly << endl;
+		assert(0);
+		return;
+	}
+#endif
+
+//	cerr << "Transform::addAddConstant(): " << p_instr->getDisassembly() << endl;
+	p_instr->setFallthrough(p_fallThrough);
+}
+
+// imul r1, constant
+void Transform::addMulRegisterConstant(Instruction_t *p_instr, RegisterName p_reg, int p_constantValue, Instruction_t *p_fallThrough)
+{
+	// too many combinations, just use the assembler
+	char buf[256];
+	sprintf(buf, "imul %s, %d", Register::toString(p_reg).c_str(), p_constantValue);
+	string assembly(buf);
+#ifdef OPTIMIZE_ASSEMBLY
+	m_fileIR->registerAssembly(p_instr, assembly);
+#else
+	if (!p_instr->Assemble(assembly))
+	{
+		cerr << "Transform::addMulRegisterConstant(): error in assembling instruction: " << assembly << endl;
+		assert(0);
+		return;
+	}
+#endif
+
+//	cerr << "Transform::addMulRegisterConstant(): " << p_instr->getDisassembly() << endl;
+	p_instr->setFallthrough(p_fallThrough);
+}
+
+
+// mov r1, r2
+void Transform::addMovRegisters(Instruction_t *p_instr, RegisterName p_regTgt, RegisterName p_regSrc, Instruction_t *p_fallThrough)
+{
+	// too many combinations, just use the assembler
+	string assembly = "mov " + Register::toString(p_regTgt) + ", " + Register::toString(p_regSrc);
+#ifdef OPTIMIZE_ASSEMBLY
+	m_fileIR->registerAssembly(p_instr, assembly);
+#else
+	if (!p_instr->Assemble(assembly))
+	{
+		cerr << "addMovRegisters(): error in assembling instruction: " << assembly << endl;
+		assert(0);
+		return;
+	}
+#endif
+	p_instr->setFallthrough(p_fallThrough);
+//	cerr << "addMovRegisters(): " << p_instr->getDisassembly() << endl;
+}
+
+void Transform::addMovRegisterSignedConstant(Instruction_t *p_instr, RegisterName p_regTgt, long int p_constant, Instruction_t *p_fallThrough)
+{
+	p_instr->setFallthrough(p_fallThrough);
+
+	char buf[128];
+
+	sprintf(buf,"mov %s, %ld", Register::toString(p_regTgt).c_str(), p_constant);
+
+	string assembly(buf);
+	m_fileIR->registerAssembly(p_instr, assembly);
+
+	p_instr->setComment("Saturating arithmetic");
+}
+
+void Transform::addMovRegisterUnsignedConstant(Instruction_t *p_instr, RegisterName p_regTgt, unsigned long int p_constant, Instruction_t *p_fallThrough)
+{
+	p_instr->setFallthrough(p_fallThrough);
+
+	char buf[128];
+	sprintf(buf,"mov %s, %lu", Register::toString(p_regTgt).c_str(), p_constant);
+
+	string assembly(buf);
+	m_fileIR->registerAssembly(p_instr, assembly);
+
+	p_instr->setComment("Saturating arithmetic");
+}
+
+void Transform::addAndRegister32Mask(Instruction_t *p_instr, RegisterName p_regTgt, unsigned int p_mask, Instruction_t *p_fallThrough)
+{
+    p_instr->setFallthrough(p_fallThrough);
+
+	char buf[128];
+	sprintf(buf,"and %s, 0x%08X", Register::toString(p_regTgt).c_str(), p_mask);
+
+    string assembly(buf);
+    cerr << "addAndRegisterMask(): assembling instruction: " << assembly << endl;
+#ifdef OPTIMIZE_ASSEMBLY
+	m_fileIR->registerAssembly(p_instr, assembly);
+#else
+    if (!p_instr->Assemble(assembly))
+    {
+        cerr << "addAndRegisterMask(): error in assembling instruction: " << assembly << endl;
+		assert(0);
+        return;
+    }
+#endif
+
+	p_instr->setComment("Saturating arithmetic by masking");
+}
+
+//-----------------------------------------------------
+// known to be used on x86-64
+//-----------------------------------------------------
+
+// hlt
+void Transform::addHlt(Instruction_t *p_instr, Instruction_t *p_fallThrough)
+{
+	string assembly("hlt");
+	m_fileIR->registerAssembly(p_instr, assembly);
+	p_instr->setFallthrough(p_fallThrough);
+}
+
+// jno - jump not overflow
+void Transform::addJno(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string assembly("jno 0x22");
+	m_fileIR->registerAssembly(p_instr, assembly);
+	p_instr->setFallthrough(p_fallThrough);
+	p_instr->setTarget(p_target);
+}
+
+// jnc - jump not carry
+void Transform::addJnc(Instruction_t *p_instr, Instruction_t *p_fallThrough, Instruction_t *p_target)
+{
+	string assembly("jnc 0x22");
+	m_fileIR->registerAssembly(p_instr, assembly);
+	p_instr->setFallthrough(p_fallThrough);
+	p_instr->setTarget(p_target);
+}
+
+Instruction_t* Transform::addNewMaxSaturation(Instruction_t *p_prev, RegisterName p_reg, const MEDS_InstructionCheckAnnotation p_annotation)
+{
+	Instruction_t *mov = allocateNewInstruction(p_prev->getAddress()->getFileID(), p_prev->getFunction());
+	if (p_prev)
+		p_prev->setFallthrough(mov);
+	addMaxSaturation(mov, p_reg, p_annotation, NULL);
+	return mov;
+}
+
+void Transform::addMaxSaturation(Instruction_t *p_instruction, RegisterName p_reg, const MEDS_InstructionCheckAnnotation& p_annotation, Instruction_t *p_fallthrough)
+{
+#if 0
+	assert(getFileIR() && p_instruction);
+
+	p_instruction->setFallthrough(p_fallthrough);
+
+	if (p_annotation.isUnsigned())
+	{
+		// use MAX_UNSIGNED for the bit width
+		switch (Register::getBitWidth(p_reg))
+		{
+			case 64:
+				addMovRegisterUnsignedConstant(p_instruction, p_reg, 0xFFFFFFFFFFFFFFFF, p_fallthrough);
+				break;
+			case 32:
+				addMovRegisterUnsignedConstant(p_instruction, p_reg, 0xFFFFFFFF, p_fallthrough);
+				break;
+			case 16:
+				addMovRegisterUnsignedConstant(p_instruction, p_reg, 0xFFFF, p_fallthrough);
+				break;
+			case 8:
+				addMovRegisterUnsignedConstant(p_instruction, p_reg, 0xFF, p_fallthrough);
+				break;
+			default:
+				cerr << "Transform::addMaxSaturation(): invalid bit width: " << p_annotation.getBitWidth() << endl;
+				break;
+		}
+	}
+	else
+	{
+		// treat unknown and signed the same way for overflows
+		// use MAX_SIGNED for the bit width
+		switch (Register::getBitWidth(p_reg))
+		{
+			case 64:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x7FFFFFFFFFFFFFFF, p_fallthrough);
+				break;
+			case 32:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x7FFFFFFF, p_fallthrough);
+				break;
+			case 16:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x7FFF, p_fallthrough);
+				break;
+			case 8:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x7F, p_fallthrough);
+				break;
+			default:
+				cerr << "Transform::addMaxSaturation(): invalid bit width: " << p_annotation.getBitWidth() << endl;
+				break;
+		}
+	}
+#else
+	// not used, and had compiler errors.
+	assert(0);
+#endif
+}
+
+void Transform::addMinSaturation(Instruction_t *p_instruction, RegisterName p_reg, const MEDS_InstructionCheckAnnotation& p_annotation, Instruction_t *p_fallthrough)
+{
+#if 0
+	assert(getFileIR() && p_instruction);
+
+	p_instruction->setFallthrough(p_fallthrough);
+
+	if (p_annotation.isUnsigned())
+	{
+		// use MIN_UNSIGNED
+		addMovRegisterUnsignedConstant(p_instruction, p_reg, 0, p_fallthrough);
+	}
+	else
+	{
+		// treat unknown and signed the same way for overflows
+		// use MIN_SIGNED for the bit width
+		switch (Register::getBitWidth(p_reg))
+		{
+			case 64:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x8000000000000000, p_fallthrough);
+				break;
+			case 32:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x80000000, p_fallthrough);
+				break;
+			case 16:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x8000, p_fallthrough);
+				break;
+			case 8:
+				addMovRegisterSignedConstant(p_instruction, p_reg, 0x80, p_fallthrough);
+				break;
+			default:
+				cerr << "Transform::addMinSaturation(): invalid bit width: " << p_annotation.getBitWidth() << endl;
+				break;
+		}
+	}
+#else
+	// not used, and had compiler errors.
+	assert(0);
+#endif
+}
+
+void Transform::setAssembly(Instruction_t *p_instr, string p_asm)
+{
+	m_fileIR->registerAssembly(p_instr, p_asm);
+}
+
+//
+// Allocate and add new instruction given its assembly form
+// If <p_instr> not NULL, then set fallthrough appropriately
+//
+// Returns the newly added instruction
+//
+// <p_instr> defined:
+// <p_instr>            <p_instr>
+// <fallthrough>  ==>   <newinstr>(<p_asm>)
+//                      <fallthrough>
+//
+// <p_instr> is NULL:
+//                ==>   <newinstr>(<p_asm>)
+//
+Instruction_t* Transform::addNewAssembly(Instruction_t *p_instr, string p_asm)
+{
+	Instruction_t* newinstr;
+	if (p_instr)
+		newinstr = allocateNewInstruction(p_instr->getAddress()->getFileID(), p_instr->getFunction());
+	else
+		newinstr = allocateNewInstruction(m_fileIR->getFile()->getFileID(), NULL);
+
+	m_fileIR->registerAssembly(newinstr, p_asm);
+
+	if (p_instr)
+	{
+		newinstr->setFallthrough(p_instr->getFallthrough());
+		p_instr->setFallthrough(newinstr);
+	}
+	else
+	{
+		newinstr->setFallthrough(NULL);
+	}
+
+	return newinstr;
+}
+
+// register instruction in IRDB
+// 20140421
+Instruction_t* Transform::addNewAssembly(string p_asm)
+{
+	return addNewAssembly(NULL, p_asm);
+}
+
+// x86-64
+// 20140421
+void Transform::addCallbackHandler64(Instruction_t *p_orig, string p_callbackHandler, int p_numArgs)
+{
+	// nb: if first time, register and cache callback handler sequence
+	if (m_handlerMap.count(p_callbackHandler) == 0)
+	{
+		m_handlerMap[p_callbackHandler] = registerCallbackHandler64(p_callbackHandler, p_numArgs);
+	}
+
+	if (p_orig)
+		p_orig->setTarget(m_handlerMap[p_callbackHandler]);
+}
+
+// x86-64
+// register callback handler sequence 
+//
+// This following note is slightly out of date.
+// We DO save flags here so that our callbacks are
+// able to look at register values using a reg_values_t.
+// HOWEVER, the caller of this function should still be sure
+// to save flags themselves.
+//
+// nb: strata semantics is that it does not save flags, so we don't bother
+//     saving/restoring flags either in the callback handler
+//     saving/restoring flags must be done outside of this routine
+// 20140416
+Instruction_t* Transform::registerCallbackHandler64(string p_callbackHandler, int p_numArgs)
+{
+	Instruction_t *instr;
+	Instruction_t *first;
+	char tmpbuf[1024];
+
+	// save flags and 16 registers (136 bytes)
+	// call pushes 8 bytes
+	// Total: 8 * 18 = 144
+	first = instr = addNewAssembly("push rsp");
+	instr = addNewAssembly(instr, "push rbp");
+	instr = addNewAssembly(instr, "push rdi");
+	instr = addNewAssembly(instr, "push rsi");
+	instr = addNewAssembly(instr, "push rdx");
+	instr = addNewAssembly(instr, "push rcx");
+	instr = addNewAssembly(instr, "push rbx");
+	instr = addNewAssembly(instr, "push rax");
+	instr = addNewAssembly(instr, "push r8");
+	instr = addNewAssembly(instr, "push r9");
+	instr = addNewAssembly(instr, "push r10");
+	instr = addNewAssembly(instr, "push r11");
+	instr = addNewAssembly(instr, "push r12");
+	instr = addNewAssembly(instr, "push r13");
+	instr = addNewAssembly(instr, "push r14");
+	instr = addNewAssembly(instr, "push r15");
+	instr = addNewAssembly(instr, "pushf");
+
+	// handle the arguments (if any): rdi, rsi, rdx, rcx, r8, r9
+	// first arg starts at byte +144
+	// now at +136??? b/c we took out the push
+	instr = addNewAssembly(instr, "mov rdi, rsp");
+
+	if (p_numArgs >= 1)
+		instr = addNewAssembly(instr,  "mov rsi, [rsp+136]");
+	if (p_numArgs >= 2)
+		instr = addNewAssembly(instr,  "mov rdx, [rsp+144]");
+	if (p_numArgs >= 3)
+		instr = addNewAssembly(instr,  "mov rcx, [rsp+152]");
+	if (p_numArgs >= 4)
+		instr = addNewAssembly(instr,  "mov r8, [rsp+160]");
+	if (p_numArgs > 4)
+		assert(0); // only handle up to 5 args
+
+	// pin the instruction that follows the callback handler
+	Instruction_t* postCallback = allocateNewInstruction();
+	VirtualOffset_t postCallbackReturn = getAvailableAddress();
+	postCallback->getAddress()->setVirtualOffset(postCallbackReturn);
+
+	// push the address to return to once the callback handler is invoked
+	sprintf(tmpbuf,"mov rax, 0x%x", (uint32_t)postCallbackReturn);
+	instr = addNewAssembly(instr, tmpbuf);
+
+	instr = addNewAssembly(instr, "push rax");
+
+	// use a nop instruction for the actual callback
+	instr = addNewAssembly(instr, "nop");
+	instr->setComment(" -- callback: " + p_callbackHandler);
+	instr->setCallback(p_callbackHandler); 
+	instr->setFallthrough(postCallback); 
+
+	// need to make sure the post callback address is pinned
+	// (so that ILR and other transforms do not relocate it)
+	AddressID_t *indTarg = new libIRDB::AddressID_t();
+	m_fileIR->GetAddresses().insert(indTarg);
+	indTarg->setVirtualOffset(postCallback->getAddress()->getVirtualOffset());
+	indTarg->setFileID(BaseObj_t::NOT_IN_DATABASE); // SPRI global namespace
+	postCallback->setIndirectBranchTargetAddress(indTarg);
+
+	// restore registers
+	setAssembly(postCallback, "popf");           
+	instr = addNewAssembly(postCallback, "pop r15");
+	instr = addNewAssembly(instr, "pop r14");
+	instr = addNewAssembly(instr, "pop r13");
+	instr = addNewAssembly(instr, "pop r12");
+	instr = addNewAssembly(instr, "pop r11");
+	instr = addNewAssembly(instr, "pop r10");
+	instr = addNewAssembly(instr, "pop r9");
+	instr = addNewAssembly(instr, "pop r8");
+	instr = addNewAssembly(instr, "pop rax");
+	instr = addNewAssembly(instr, "pop rbx");
+	instr = addNewAssembly(instr, "pop rcx");
+	instr = addNewAssembly(instr, "pop rdx");
+	instr = addNewAssembly(instr, "pop rsi");
+	instr = addNewAssembly(instr, "pop rdi");
+	instr = addNewAssembly(instr, "pop rbp");
+	instr = addNewAssembly(instr, "lea rsp, [rsp+8]");
+
+	instr = addNewAssembly(instr, "ret");
+
+	// return first instruction in the callback handler chain
+	return first;
+}
+
+void Transform::logMessage(const std::string &p_method, const std::string &p_msg)
+{
+	std::cerr << p_method << ": " << p_msg << std::endl;
+}
+
+void Transform::logMessage(const std::string &p_method, const MEDS_InstructionCheckAnnotation& p_annotation, const std::string &p_msg)
+{
+	logMessage(p_method, p_msg + " annotation: " + p_annotation.toString());
+}
+
+void libTransform::convertToLowercase(string &str)
+{
+	for (auto i = 0U; i < str.length(); ++i)
+	{
+		str[i] = tolower(str[i]);
+	}
+}
+
+#endif
+
+
diff --git a/irdb-lib/libIRDB-util/include/IBT_Provenance.hpp b/irdb-lib/libIRDB-util/include/IBT_Provenance.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..3aba669af6eca86d5688f0d144cf5a5fb35c3339
--- /dev/null
+++ b/irdb-lib/libIRDB-util/include/IBT_Provenance.hpp
@@ -0,0 +1,43 @@
+#ifndef IBT_Provenance_h
+#define IBT_Provenance_h
+
+#include "Provenance.hpp"
+
+class IBTProvenance_t : public IRDB_SDK::IBTProvenance_t
+{
+	private:
+
+	// types 
+	using InsnProvMap_t =  std::map<const IRDB_SDK::Instruction_t*, Provenance_t>;
+
+	// data
+	InsnProvMap_t prov_map;
+	static Provenance_t empty;
+
+	// methods
+	void Init() {};
+	void AddProvs(const Provenance_t& p, const InstructionSet_t& after) ;
+
+	public:
+	IBTProvenance_t(const IRDB_SDK::FileIR_t* f=NULL) {Init(); if(f) addFile(f);}
+	virtual ~IBTProvenance_t() {} 	// default destructor not OK for some reason?
+	void addFile(const IRDB_SDK::FileIR_t* );
+        
+	const Provenance_t& getProvenance (const IRDB_SDK::Instruction_t* i)  const
+	{
+		return (*this)[i];
+	}
+
+	const Provenance_t& operator[] (const IRDB_SDK::Instruction_t* i)  const
+	{ 
+		const auto it=prov_map.find(i);
+		if (it!= prov_map.end()) 
+			return it->second;
+		return empty;
+	}
+ 
+
+};
+
+#endif
+
diff --git a/irdb-lib/libIRDB-util/include/Provenance.hpp b/irdb-lib/libIRDB-util/include/Provenance.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..520ac73da6518bbcc6faa7dcfae436d9c795d306
--- /dev/null
+++ b/irdb-lib/libIRDB-util/include/Provenance.hpp
@@ -0,0 +1,53 @@
+#ifndef Provenance_h
+#define Provenance_h
+
+#include <bitset>
+
+class Provenance_t : public IRDB_SDK::Provenance_t
+{
+	private:
+		// ProvType enum values are explicit to show they are in bounds of the bitset
+		enum class ProvType { IndJump = 0, IndCall = 1, Ret = 2 };
+		std::bitset<3> prov;
+	public:
+		Provenance_t() {prov = std::bitset<3>();}
+		virtual ~Provenance_t() {;}
+
+		void addReturn()
+		{
+			prov.set((size_t) ProvType::Ret);
+		}
+
+		void addIndirectJump()
+		{
+			prov.set((size_t) ProvType::IndJump);
+		}
+
+		void addIndirectCall()
+		{
+			prov.set((size_t) ProvType::IndCall);
+		}
+
+		void addProv(const Provenance_t& other)
+		{
+			prov |= other.prov;
+		}
+
+		bool hasReturn() const
+		{
+			return prov.test((size_t) ProvType::Ret);
+		}
+
+		
+		bool hasIndirectJump() const
+		{
+			return prov.test((size_t) ProvType::IndJump);
+		}
+
+		bool hasIndirectCall() const
+                {
+                        return prov.test((size_t) ProvType::IndCall);
+                }
+};		
+
+#endif
diff --git a/irdb-lib/libIRDB-util/include/insn_preds.hpp b/irdb-lib/libIRDB-util/include/insn_preds.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..3078d25b8272aa235781261306fe033e106f9298
--- /dev/null
+++ b/irdb-lib/libIRDB-util/include/insn_preds.hpp
@@ -0,0 +1,61 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef insn_preds_h
+#define insn_preds_h
+
+
+class InstructionPredecessors_t : public IRDB_SDK::InstructionPredecessors_t
+{
+	private:
+	typedef std::map<const IRDB_SDK::Instruction_t*, InstructionSet_t> PredMap_t;
+
+	public:
+	InstructionPredecessors_t(const IRDB_SDK::FileIR_t* f=NULL) {Init(); if(f) AddFile(f);}
+        virtual ~InstructionPredecessors_t() {;}
+	virtual void AddFile(const IRDB_SDK::FileIR_t* );
+
+	virtual const InstructionSet_t& getPredecessors(const IRDB_SDK::Instruction_t* i)  const { return (*this)[i]; } 
+
+	InstructionSet_t& operator[] (const IRDB_SDK::Instruction_t* i)  
+		{
+			return pred_map[i];
+		}
+	const InstructionSet_t& operator[] (const IRDB_SDK::Instruction_t* i)  const
+		{ 
+			PredMap_t::const_iterator it=pred_map.find(i);
+			if (it!= pred_map.end()) 
+				return it->second;
+			static InstructionSet_t empty;
+			return empty;
+		}
+
+	protected:
+	virtual void Init() {};
+
+	private:
+
+	virtual void AddPred(const IRDB_SDK::Instruction_t* before, const IRDB_SDK::Instruction_t* after);
+	virtual void AddPreds(const IRDB_SDK::Instruction_t* before, const IRDB_SDK::InstructionSet_t& after);
+
+	PredMap_t pred_map;
+};
+
+#endif
diff --git a/irdb-lib/libIRDB-util/include/libIRDB-util.hpp b/irdb-lib/libIRDB-util/include/libIRDB-util.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..5b091d1165fab6cc1aa9edf3060a2a88e908c445
--- /dev/null
+++ b/irdb-lib/libIRDB-util/include/libIRDB-util.hpp
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef libIRDB_util
+#define libIRDB_util
+
+
+/* Building a CFG depends on core functionality */
+#include <irdb-core>
+#include <irdb-util>
+#include <libIRDB-core.hpp>
+
+#include <vector>
+#include <set>
+#include <map>
+#include <ostream>
+
+namespace libIRDB 
+{
+
+#include <insn_preds.hpp>
+#include <IBT_Provenance.hpp>
+#include <params.hpp>
+
+};
+
+#endif
diff --git a/irdb-lib/libIRDB-util/include/params.hpp b/irdb-lib/libIRDB-util/include/params.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391
diff --git a/irdb-lib/libIRDB-util/src/IBT_Provenance.cpp b/irdb-lib/libIRDB-util/src/IBT_Provenance.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..978fdc9d5ffe7df5e151dc4d98554f0a1f3f74a5
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/IBT_Provenance.cpp
@@ -0,0 +1,70 @@
+#include <map>
+#include <bitset>
+#include <libIRDB-core.hpp>
+#include <libIRDB-util.hpp>
+#include <irdb-util>
+
+using namespace libIRDB;
+using namespace std;
+
+
+Provenance_t IBTProvenance_t::empty;
+
+
+void IBTProvenance_t::addFile(const IRDB_SDK::FileIR_t* firp)
+{
+
+        using ICFSProvMap_t =  std::map<const IRDB_SDK::ICFS_t*, Provenance_t>;
+
+	auto icfs_prov_map = ICFSProvMap_t(); 
+
+	// collect before info for each icfs into icfs_prov_map
+	for(auto insn : firp->getInstructions())
+	{
+		const auto &ibTargets=insn->getIBTargets();
+		if(!ibTargets)
+			continue;
+
+		libIRDB::Provenance_t this_prov;
+		const auto p_IndBranchAsm=DecodedInstruction_t::factory(insn);
+		const auto &IndBranchAsm=*p_IndBranchAsm;
+		const auto isIndJmp = IndBranchAsm.isUnconditionalBranch() && !IndBranchAsm.getOperand(0)->isConstant();
+		const auto isIndCall = IndBranchAsm.isCall() && !IndBranchAsm.getOperand(0)->isConstant();
+		const auto isRet = IndBranchAsm.isReturn();
+
+		if(isIndJmp)
+		{
+			this_prov.addIndirectJump();
+		}
+		else if(isIndCall)
+		{
+			this_prov.addIndirectCall();
+		}
+		else if(isRet)
+		{
+			this_prov.addReturn();
+		}
+		else
+		{
+			assert(0);
+		}
+
+		icfs_prov_map[ibTargets].addProv(this_prov);
+	}
+
+	// deploy info for each target of the icfs
+	for(const auto &icfs : firp->getAllICFS())
+	{
+		assert(icfs);
+		for(const auto &insn : *icfs)
+		{
+			prov_map[insn].addProv(icfs_prov_map[icfs]);
+		}
+	}
+}
+
+unique_ptr<IRDB_SDK::IBTProvenance_t> IRDB_SDK::IBTProvenance_t::factory(const IRDB_SDK::FileIR_t* f)
+{
+	return unique_ptr<IRDB_SDK::IBTProvenance_t>(new libIRDB::IBTProvenance_t(f));
+}
+
diff --git a/irdb-lib/libIRDB-util/src/Makefile b/irdb-lib/libIRDB-util/src/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..964ec5464c1c65bcd3a0c75f4ea40d8a420553d9
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/Makefile
@@ -0,0 +1,15 @@
+
+LIB=../../lib/libIRDB-util.a
+
+OBJS=insn_preds.o
+
+all: $(OBJS)
+
+$(OBJS): ../../include/core/*.hpp ../../include/util/*.hpp ../../include/*.hpp 
+
+clean:
+	rm -f $(OBJS)
+
+.cpp.o:
+	$(CXX) -fPIC -g -c -I. -I../../include -I../../../beaengine/include $<
+	ar rc $(LIB) $@
diff --git a/irdb-lib/libIRDB-util/src/SConscript b/irdb-lib/libIRDB-util/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..fee25b597ad027296a0ee24b950916fb0105c8e0
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/SConscript
@@ -0,0 +1,31 @@
+import os
+
+Import('env')
+myenv=env
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+libname="irdb-util"
+files=  '''
+	insn_preds.cpp
+        IBT_Provenance.cpp
+	params.cpp
+	registers.cpp
+	'''
+cpppath=''' 
+	$IRDB_SDK/include/
+	$SECURITY_TRANSFORMS_HOME/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-core/include/
+	$SECURITY_TRANSFORMS_HOME/libIRDB-util/include/
+	'''
+
+#myenv.Append(CCFLAGS=" -Wall -W -Wextra -Wconversion ")
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS = " -std=c++11 ")
+lib=myenv.SharedLibrary(libname, Split(files), LIBS=Split("irdb-core"), LIBPATH=Split("$SECURITY_TRANSFORMS_HOME/lib"))
+
+install=env.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libIRDB-util/src/SConstruct b/irdb-lib/libIRDB-util/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..17f632b8c29cd420163897b1eb044ca3486df362
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+install=SConscript("SConscript")
+Return('install')
diff --git a/irdb-lib/libIRDB-util/src/insn_preds.cpp b/irdb-lib/libIRDB-util/src/insn_preds.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..405b737afddce242139f4dc332ba1cb95e633c28
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/insn_preds.cpp
@@ -0,0 +1,73 @@
+/*
+ * Copyright (c) 2014-2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <map>
+#include <libIRDB-core.hpp>
+#include <libIRDB-util.hpp>
+#include <irdb-util>
+
+using namespace libIRDB;
+using namespace std;
+
+
+
+void InstructionPredecessors_t::AddPreds(const IRDB_SDK::Instruction_t* before, const InstructionSet_t& afterset)
+{
+	for(auto it=afterset.begin(); it!=afterset.end(); ++it)
+	{
+		pred_map[*it].insert(const_cast<IRDB_SDK::Instruction_t*>(before));
+	}
+}
+
+void InstructionPredecessors_t::AddPred(const IRDB_SDK::Instruction_t* before, const IRDB_SDK::Instruction_t* after)
+{
+	assert(before);
+	if(!after) return;
+
+	if(getenv("DUMP_PRED_CREATE"))
+		cout<<"Found "<<after->getBaseID()<<":"<<after->getDisassembly() << " follows "<< before->getBaseID()<<":"<<before->getDisassembly()<<endl;
+	pred_map[after].insert(const_cast<IRDB_SDK::Instruction_t*>(before));
+	
+}
+
+void InstructionPredecessors_t::AddFile(const IRDB_SDK::FileIR_t* firp2)
+{
+	auto firp=const_cast<IRDB_SDK::FileIR_t*>(firp2); // discarding const qualifier because we know we won't change the set
+	for(auto it=firp->getInstructions().begin();
+		it!=firp->getInstructions().end();
+		++it)
+	{
+		auto insn=*it;
+		AddPred(insn, insn->getTarget());
+		AddPred(insn, insn->getFallthrough());
+
+		// if we have a complete list, then explicitly add them.
+	        if(insn->getIBTargets() && insn->getIBTargets()->isComplete())
+        	      	AddPreds(insn, *insn->getIBTargets());
+		
+	}
+}
+
+unique_ptr<IRDB_SDK::InstructionPredecessors_t> IRDB_SDK::InstructionPredecessors_t::factory(IRDB_SDK::FileIR_t* firp)
+{
+	return unique_ptr<IRDB_SDK::InstructionPredecessors_t>(new libIRDB::InstructionPredecessors_t(firp));
+}
+
diff --git a/irdb-lib/libIRDB-util/src/params.cpp b/irdb-lib/libIRDB-util/src/params.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..68bab5b3aa27ff385ba45e3b893c8eac37eaa7cc
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/params.cpp
@@ -0,0 +1,255 @@
+/*
+ * Copyright (c) 2014-2017 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#include <libIRDB-core.hpp>
+#include <libIRDB-util.hpp>
+#include <irdb-util>
+#include <algorithm>
+
+using namespace libIRDB;
+using namespace std;
+
+// Does instruction potentially write to a parameter to a call?
+bool IRDB_SDK::isParameterWrite(const IRDB_SDK::FileIR_t *firp, IRDB_SDK::Instruction_t* insn, string& output_dst)
+{
+	const auto p_d=DecodedInstruction_t::factory(insn);
+	const auto &d=*p_d;
+
+	if(!d.hasOperand(0))
+		return false;
+	if(!d.getOperand(0)->isWritten())
+		return false;
+
+	/* 64 bit machines use regs to pass parameters */
+	if(firp->getArchitectureBitWidth()==64)
+	{
+		// if it's a register
+		if(d.getOperand(0)->isGeneralPurposeRegister())
+		{
+			int regno=d.getOperand(0)->getRegNumber();
+			switch(regno)
+			{
+				case 1:  // rcx?
+				case 2:  // rdx?
+				case 6:  // rsi?
+				case 7:  // rdi?
+				case 8:  // r8?
+				case 9:  // r9?
+					output_dst=d.getOperand(0)->getString();
+					return true;
+
+				// other regsiters == no.
+				default:
+					return false;
+			}
+
+		}
+	}
+
+	// not a register or not 64-bit.  check for [esp+k]
+
+	// check for memory type
+	if(!d.getOperand(0)->isMemory())
+		return false;
+
+	// check that base reg is esp.
+	if(!d.getOperand(0)->hasBaseRegister())
+		return false;
+	if(d.getOperand(0)->getBaseRegister() != 4)
+		return false;
+
+	// check that there's no index reg
+	if(d.getOperand(0)->hasIndexRegister())
+		return false;
+
+	// get k out of [esp + k ]
+	if (!d.getOperand(0)->hasMemoryDisplacement())
+		return false;
+	const auto k=d.getOperand(0)->getMemoryDisplacement();
+
+	// check that we know the frame layout.
+	if(insn->getFunction() == NULL)
+		return false;
+
+	if(k < insn->getFunction()->getOutArgsRegionSize())
+	{
+		output_dst=string("[")+d.getOperand(0)->getString()+string("]");
+		return true;
+	}
+
+	// return we didn't find a memory of the right type
+	return false;
+}
+
+//
+// we look for:
+//    (1) call instruction
+//    (2) call converted to push/jmp pair
+//
+IRDB_SDK::Instruction_t* isOrWasCall(const IRDB_SDK::FileIR_t *firp, IRDB_SDK::Instruction_t* insn)
+{
+	if (firp == NULL || insn == NULL)
+		return NULL;
+
+	const auto p_d=DecodedInstruction_t::factory(insn);
+	const auto &d=*p_d;
+
+	if(d.isCall())
+	{
+		return insn->getTarget();
+	}
+	else 
+	{
+		// look for "push64" or "fix_call_fallthrough" reloc
+		auto it = std::find_if(insn->getRelocations().begin(),insn->getRelocations().end(),[&](const IRDB_SDK::Relocation_t* reloc) 
+		{
+			return (reloc && ((reloc->getType() == string("push64")) || reloc->getType() == string("fix_call_fallthrough")));
+		});
+
+		// find actual target
+		if (it != insn->getRelocations().end())
+		{
+			if (insn->getTarget())
+				return insn->getTarget();
+			else if (insn->getFallthrough())
+				return insn->getFallthrough()->getTarget();
+		}
+	}
+
+	return NULL;
+}
+
+// Does a call follow the instruction?
+bool IRDB_SDK::callFollows(const IRDB_SDK::FileIR_t *firp, IRDB_SDK::Instruction_t* insn, const string& reg_arg_str, const std::string &fn_pattern)
+{
+	const std::set<std::string> param_regs = {"rdi", "rsi", "rdx", "rcx", "r8", "r9"};
+	const bool original_is_param_register = param_regs.find(reg_arg_str) != param_regs.end();
+
+	std::set<std::string> live_params;
+	live_params.insert(reg_arg_str);
+	
+	for(auto ptr=insn->getFallthrough(); ptr!=NULL; ptr=ptr->getFallthrough())
+	{
+		const auto p_d=DecodedInstruction_t::factory(ptr);
+		const auto &d=*p_d;
+		const auto tgt = isOrWasCall(firp, ptr);
+
+		if (tgt) 
+		{
+			if (fn_pattern.size() == 0)
+			{
+				// don't care about function name
+//				std::cout << "CallFollows(): yes, parameter to call" << endl;
+				return true;
+			}
+			else 
+			{
+				// look for specific function
+
+				// check the target has a function 
+				if(tgt->getFunction()==NULL) 
+					return false;
+
+				const auto fname = tgt->getFunction()->getName();
+//				std::cout << "CallFollows(): yes, parameter to call: function name: " << fname << endl;
+				return fname.find(fn_pattern)!=string::npos;
+			}
+		}
+
+		// found reference to argstring, original code would just stop the search
+		// need more sophisticated heuristic
+		if(d.getDisassembly().find(reg_arg_str)!= string::npos)
+		{
+			if (original_is_param_register)
+			{
+				std::string arg;
+				if (isParameterWrite(firp, ptr, arg))
+				{
+//					std::cout << "CallFollows(): " << ptr->getDisassembly() << ": detected write parameter" << std::endl;
+ 					if (arg == reg_arg_str)
+					{
+//						std::cout << "CallFollows(): " << ptr->getDisassembly() << ": same parameter as original: remove from live list: " << reg_arg_str << std::endl;
+						live_params.erase(reg_arg_str);
+					}
+					else 
+					{
+						if (d.hasOperand(1) && d.getOperand(1)->getString() == reg_arg_str) 
+						{
+//							std::cout << "CallFollows(): " << ptr->getDisassembly() << ": copy of original detected: add to live list: " << arg << std::endl;
+							live_params.insert(arg);
+						}
+					}
+				}
+
+				std::cout << "CallFollows(): " << ptr->getDisassembly() << ": #live_param: " << dec << live_params.size() << std::endl;
+				if (live_params.size() == 0)
+				{
+//					std::cout << "CallFollows(): not a parameter to call" << endl;
+					return false;
+				}
+			}
+			else
+			{
+//				std::cout << "\tassume it's a write and exit" << std::endl;
+				return false;
+			}
+
+		}
+	}
+
+//	std::cout << "CallFollows(): no more fallthroughs, not a parameter to call" << endl;
+	return false;
+}
+
+bool IRDB_SDK::flowsIntoCall(const IRDB_SDK::FileIR_t *firp, IRDB_SDK::Instruction_t* insn)
+{
+	string param_write;
+	if (!isParameterWrite(firp, insn, param_write))
+		return false;
+
+	return callFollows(firp, insn, param_write);
+}
+
+bool IRDB_SDK::leaFlowsIntoCall(const IRDB_SDK::FileIR_t *firp, IRDB_SDK::Instruction_t* insn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+	if (d->getMnemonic()!="lea")
+		return false;
+
+	return flowsIntoCall(firp, insn);
+}
+
+bool IRDB_SDK::leaFlowsIntoPrintf(const IRDB_SDK::FileIR_t *firp, IRDB_SDK::Instruction_t* insn)
+{
+	const auto d=DecodedInstruction_t::factory(insn);
+
+	if (d->getMnemonic()!="lea")
+		return false;
+
+//	std::cout << "LeaFlowsIntoCall(): investigating " << insn->getDisassembly() << endl;
+
+	string param_write;
+	if (!isParameterWrite(firp, insn, param_write))
+		return false;
+
+	return callFollows(firp, insn, param_write, "printf");
+}
diff --git a/irdb-lib/libIRDB-util/src/registers.cpp b/irdb-lib/libIRDB-util/src/registers.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b9ee000e008a2e4cb46da90bd747d80a348769cc
--- /dev/null
+++ b/irdb-lib/libIRDB-util/src/registers.cpp
@@ -0,0 +1,423 @@
+
+
+#include <string>
+#include <irdb-util> 
+
+using namespace std;
+using namespace IRDB_SDK;
+
+RegisterID_t IRDB_SDK::strToRegister(const char *p_reg)
+{
+	return strToRegister(string(p_reg));
+}
+
+bool IRDB_SDK::isValidRegister(const RegisterID_t p_reg)
+{
+	return p_reg != rn_UNKNOWN;
+}
+
+RegisterID_t IRDB_SDK::strToRegister(const string& p_reg)
+{
+	if (strcasecmp(p_reg.c_str(), "EFLAGS") ==0)
+		return rn_EFLAGS;
+	else if (strcasecmp(p_reg.c_str(), "RAX") == 0)
+		return rn_RAX;
+	else if (strcasecmp(p_reg.c_str(), "RBX") == 0)
+		return rn_RBX;
+	else if (strcasecmp(p_reg.c_str(), "RCX") == 0)
+		return rn_RCX;
+	else if (strcasecmp(p_reg.c_str(), "RDX") == 0)
+		return rn_RDX;
+	else if (strcasecmp(p_reg.c_str(), "RSI") == 0)
+		return rn_RSI;
+	else if (strcasecmp(p_reg.c_str(), "RDI") == 0)
+		return rn_RDI;
+	else if (strcasecmp(p_reg.c_str(), "RBP") == 0)
+		return rn_RBP;
+	else if (strcasecmp(p_reg.c_str(), "RSP") == 0)
+		return rn_RSP;
+	else if (strcasecmp(p_reg.c_str(), "R8") == 0)
+		return rn_R8;
+	else if (strcasecmp(p_reg.c_str(), "R9") == 0)
+		return rn_R9;
+	else if (strcasecmp(p_reg.c_str(), "R10") == 0)
+		return rn_R10;
+	else if (strcasecmp(p_reg.c_str(), "R11") == 0)
+		return rn_R11;
+	else if (strcasecmp(p_reg.c_str(), "R12") == 0)
+		return rn_R12;
+	else if (strcasecmp(p_reg.c_str(), "R13") == 0)
+		return rn_R13;
+	else if (strcasecmp(p_reg.c_str(), "R14") == 0)
+		return rn_R14;
+	else if (strcasecmp(p_reg.c_str(), "R15") == 0)
+		return rn_R15;
+	else if (strcasecmp(p_reg.c_str(), "RIP") == 0)
+		return rn_RIP;
+
+	else if (strcasecmp(p_reg.c_str(), "EAX") == 0)
+		return rn_EAX;
+	else if (strcasecmp(p_reg.c_str(), "EBX") == 0)
+		return rn_EBX;
+	else if (strcasecmp(p_reg.c_str(), "ECX") == 0)
+		return rn_ECX;
+	else if (strcasecmp(p_reg.c_str(), "EDX") == 0)
+		return rn_EDX;
+	else if (strcasecmp(p_reg.c_str(), "ESI") == 0)
+		return rn_ESI;
+	else if (strcasecmp(p_reg.c_str(), "EDI") == 0)
+		return rn_EDI;
+	else if (strcasecmp(p_reg.c_str(), "EBP") == 0)
+		return rn_EBP;
+	else if (strcasecmp(p_reg.c_str(), "ESP") == 0)
+		return rn_ESP;
+	else if (strcasecmp(p_reg.c_str(), "R8D") == 0)
+		return rn_R8D;
+	else if (strcasecmp(p_reg.c_str(), "R9D") == 0)
+		return rn_R9D;
+	else if (strcasecmp(p_reg.c_str(), "R10D") == 0)
+		return rn_R10D;
+	else if (strcasecmp(p_reg.c_str(), "R11D") == 0)
+		return rn_R11D;
+	else if (strcasecmp(p_reg.c_str(), "R12D") == 0)
+		return rn_R12D;
+	else if (strcasecmp(p_reg.c_str(), "R13D") == 0)
+		return rn_R13D;
+	else if (strcasecmp(p_reg.c_str(), "R14D") == 0)
+		return rn_R14D;
+	else if (strcasecmp(p_reg.c_str(), "R15D") == 0)
+		return rn_R15D;
+
+	else if (strcasecmp(p_reg.c_str(), "AX") == 0)
+		return rn_AX;
+	else if (strcasecmp(p_reg.c_str(), "BX") == 0)
+		return rn_BX;
+	else if (strcasecmp(p_reg.c_str(), "CX") == 0)
+		return rn_CX;
+	else if (strcasecmp(p_reg.c_str(), "DX") == 0)
+		return rn_DX;
+	else if (strcasecmp(p_reg.c_str(), "BP") == 0)
+		return rn_BP;
+	else if (strcasecmp(p_reg.c_str(), "SP") == 0)
+		return rn_SP;
+	else if (strcasecmp(p_reg.c_str(), "SI") == 0)
+		return rn_SI;
+	else if (strcasecmp(p_reg.c_str(), "DI") == 0)
+		return rn_DI;
+	else if (strcasecmp(p_reg.c_str(), "R8W") == 0)
+		return rn_R8W;
+	else if (strcasecmp(p_reg.c_str(), "R9W") == 0)
+		return rn_R9W;
+	else if (strcasecmp(p_reg.c_str(), "R10W") == 0)
+		return rn_R10W;
+	else if (strcasecmp(p_reg.c_str(), "R11W") == 0)
+		return rn_R11W;
+	else if (strcasecmp(p_reg.c_str(), "R12W") == 0)
+		return rn_R12W;
+	else if (strcasecmp(p_reg.c_str(), "R13W") == 0)
+		return rn_R13W;
+	else if (strcasecmp(p_reg.c_str(), "R14W") == 0)
+		return rn_R14W;
+	else if (strcasecmp(p_reg.c_str(), "R15W") == 0)
+		return rn_R15W;
+
+	else if (strcasecmp(p_reg.c_str(), "AH") == 0)
+		return rn_AL;
+	else if (strcasecmp(p_reg.c_str(), "BH") == 0)
+		return rn_BL;
+	else if (strcasecmp(p_reg.c_str(), "CH") == 0)
+		return rn_CL;
+	else if (strcasecmp(p_reg.c_str(), "DH") == 0)
+		return rn_DL;
+	else if (strcasecmp(p_reg.c_str(), "AL") == 0)
+		return rn_AL;
+	else if (strcasecmp(p_reg.c_str(), "BL") == 0)
+		return rn_BL;
+	else if (strcasecmp(p_reg.c_str(), "CL") == 0)
+		return rn_CL;
+	else if (strcasecmp(p_reg.c_str(), "DL") == 0)
+		return rn_DL;
+	else if (strcasecmp(p_reg.c_str(), "SIL") == 0)
+		return rn_SIL;
+	else if (strcasecmp(p_reg.c_str(), "DIL") == 0)
+		return rn_DIL;
+	else if (strcasecmp(p_reg.c_str(), "BPL") == 0)
+		return rn_BPL;
+	else if (strcasecmp(p_reg.c_str(), "SPL") == 0)
+		return rn_SPL;
+	else if (strcasecmp(p_reg.c_str(), "R8B") == 0)
+		return rn_R8B;
+	else if (strcasecmp(p_reg.c_str(), "R9B") == 0)
+		return rn_R9B;
+	else if (strcasecmp(p_reg.c_str(), "R10B") == 0)
+		return rn_R10B;
+	else if (strcasecmp(p_reg.c_str(), "R11B") == 0)
+		return rn_R11B;
+	else if (strcasecmp(p_reg.c_str(), "R12B") == 0)
+		return rn_R12B;
+	else if (strcasecmp(p_reg.c_str(), "R13B") == 0)
+		return rn_R13B;
+	else if (strcasecmp(p_reg.c_str(), "R14B") == 0)
+		return rn_R14B;
+	else if (strcasecmp(p_reg.c_str(), "R15B") == 0)
+		return rn_R15B;
+	else
+		return rn_UNKNOWN;
+}
+
+bool IRDB_SDK::is8bitRegister(const RegisterID_t p_reg)
+{
+	return p_reg == rn_AL || p_reg == rn_BL || p_reg == rn_CL || p_reg == rn_DL ||
+		p_reg == rn_AH || p_reg == rn_BH || p_reg == rn_CH || p_reg == rn_DH ||
+		p_reg == rn_SIL || p_reg == rn_DIL || p_reg == rn_BPL || p_reg == rn_SPL ||
+		p_reg == rn_R8B || p_reg == rn_R9B || p_reg == rn_R10B || p_reg == rn_R11B ||
+		p_reg == rn_R12B || p_reg == rn_R13B || p_reg == rn_R14B || p_reg == rn_R15B;
+}
+
+bool IRDB_SDK::is16bitRegister(const RegisterID_t p_reg)
+{
+	return p_reg == rn_AX || p_reg == rn_BX || p_reg == rn_CX || p_reg == rn_DX ||
+		p_reg == rn_BP || p_reg == rn_SP || p_reg == rn_SI || p_reg == rn_DI ||
+		p_reg == rn_R8W || p_reg == rn_R9W || p_reg == rn_R10W || p_reg == rn_R11W ||
+		p_reg == rn_R12W || p_reg == rn_R13W || p_reg == rn_R14W || p_reg == rn_R15W;
+}
+
+bool IRDB_SDK::is32bitRegister(const RegisterID_t p_reg)
+{
+	return p_reg == rn_EAX || p_reg == rn_EBX || p_reg == rn_ECX || p_reg == rn_EDX || 
+		p_reg == rn_ESI || p_reg == rn_EDI || p_reg == rn_ESP || p_reg == rn_EBP ||
+		p_reg == rn_R8D || p_reg == rn_R9D || p_reg == rn_R10D || p_reg == rn_R11D ||
+		p_reg == rn_R12D || p_reg == rn_R13D || p_reg == rn_R14D || p_reg == rn_R15D;
+}
+
+bool IRDB_SDK::is64bitRegister(const RegisterID_t p_reg)
+{
+	return p_reg == rn_RAX || p_reg == rn_RBX || p_reg == rn_RCX || p_reg == rn_RDX || 
+		p_reg == rn_RSI || p_reg == rn_RDI || p_reg == rn_RBP || p_reg == rn_RSP ||
+		p_reg == rn_R8 || p_reg == rn_R9 || p_reg == rn_R10 || p_reg == rn_R11 || 
+		p_reg == rn_R12 || p_reg == rn_R13 || p_reg == rn_R14 || p_reg == rn_R15 || p_reg == rn_RIP;
+}
+
+string IRDB_SDK::registerToString(const RegisterID_t p_reg)
+{
+	if (p_reg == rn_UNKNOWN) return string("UNKNOWN");
+
+	else if (p_reg == rn_EFLAGS) return string("EFLAGS");
+
+	else if (p_reg == rn_RAX) return string("RAX");
+	else if (p_reg == rn_RBX) return string("RBX");
+	else if (p_reg == rn_RCX) return string("RCX");
+	else if (p_reg == rn_RDX) return string("RDX");
+	else if (p_reg == rn_RSI) return string("RSI");
+	else if (p_reg == rn_RDI) return string("RDI");
+	else if (p_reg == rn_RBP) return string("RBP");
+	else if (p_reg == rn_RSP) return string("RSP");
+	else if (p_reg == rn_R8) return string("R8");
+	else if (p_reg == rn_R9) return string("R9");
+	else if (p_reg == rn_R10) return string("R10");
+	else if (p_reg == rn_R11) return string("R11");
+	else if (p_reg == rn_R12) return string("R12");
+	else if (p_reg == rn_R13) return string("R13");
+	else if (p_reg == rn_R14) return string("R14");
+	else if (p_reg == rn_R15) return string("R15");
+	else if (p_reg == rn_RIP) return string("RIP");
+
+	else if (p_reg == rn_EAX) return string("EAX");
+	else if (p_reg == rn_EBX) return string("EBX");
+	else if (p_reg == rn_ECX) return string("ECX");
+	else if (p_reg == rn_EDX) return string("EDX");
+	else if (p_reg == rn_EDI) return string("EDI");
+	else if (p_reg == rn_ESI) return string("ESI");
+	else if (p_reg == rn_EBP) return string("EBP");
+	else if (p_reg == rn_ESP) return string("ESP");
+	else if (p_reg == rn_R8D) return string("R8D");
+	else if (p_reg == rn_R9D) return string("R9D");
+	else if (p_reg == rn_R10D) return string("R10D");
+	else if (p_reg == rn_R11D) return string("R11D");
+	else if (p_reg == rn_R12D) return string("R12D");
+	else if (p_reg == rn_R13D) return string("R13D");
+	else if (p_reg == rn_R14D) return string("R14D");
+	else if (p_reg == rn_R15D) return string("R15D");
+
+	else if (p_reg == rn_AX) return string("AX");
+	else if (p_reg == rn_BX) return string("BX");
+	else if (p_reg == rn_CX) return string("CX");
+	else if (p_reg == rn_DX) return string("DX");
+	else if (p_reg == rn_BP) return string("BP");
+	else if (p_reg == rn_SP) return string("SP");
+	else if (p_reg == rn_SI) return string("SI");
+	else if (p_reg == rn_DI) return string("DI");
+	else if (p_reg == rn_R8W) return string("R8W");
+	else if (p_reg == rn_R9W) return string("R9W");
+	else if (p_reg == rn_R10W) return string("R10W");
+	else if (p_reg == rn_R11W) return string("R11W");
+	else if (p_reg == rn_R12W) return string("R12W");
+	else if (p_reg == rn_R13W) return string("R13W");
+	else if (p_reg == rn_R14W) return string("R14W");
+	else if (p_reg == rn_R15W) return string("R15W");
+
+	else if (p_reg == rn_AH) return string("AH");
+	else if (p_reg == rn_BH) return string("BH");
+	else if (p_reg == rn_CH) return string("CH");
+	else if (p_reg == rn_DH) return string("DH");
+	else if (p_reg == rn_AL) return string("AL");
+	else if (p_reg == rn_BL) return string("BL");
+	else if (p_reg == rn_CL) return string("CL");
+	else if (p_reg == rn_DL) return string("DL");
+	else if (p_reg == rn_SIL) return string("SIL");
+	else if (p_reg == rn_DIL) return string("DIL");
+	else if (p_reg == rn_BPL) return string("BPL");
+	else if (p_reg == rn_SPL) return string("SPL");
+	else if (p_reg == rn_R8B) return string("R8B");
+	else if (p_reg == rn_R9B) return string("R9B");
+	else if (p_reg == rn_R10B) return string("R10B");
+	else if (p_reg == rn_R11B) return string("R11B");
+	else if (p_reg == rn_R12B) return string("R12B");
+	else if (p_reg == rn_R13B) return string("R13B");
+	else if (p_reg == rn_R14B) return string("R14B");
+	else if (p_reg == rn_R15B) return string("R15B");
+
+	else return string("UNEXPECTED REGISTER VALUE");
+}
+
+
+RegisterID_t IRDB_SDK::convertRegisterTo64bit(const RegisterID_t p_reg)
+{
+	if (is64bitRegister(p_reg))
+		return p_reg;
+
+	switch (p_reg)
+	{
+		case rn_AL:				
+		case rn_AH:				
+		case rn_AX:				
+		case rn_EAX:
+			return rn_RAX;
+		case rn_BL:				
+		case rn_BH:				
+		case rn_BX:				
+		case rn_EBX:
+			return rn_RBX;
+		case rn_CL:				
+		case rn_CH:				
+		case rn_CX:				
+		case rn_ECX:
+			return rn_RCX;
+		case rn_DL:				
+		case rn_DH:				
+		case rn_DX:				
+		case rn_EDX:
+			return rn_RDX;
+		case rn_DIL:
+		case rn_DI:				
+		case rn_EDI:
+			return rn_RDI;
+		case rn_SIL:
+		case rn_SI:				
+		case rn_ESI:
+			return rn_RSI;
+		case rn_BPL:
+		case rn_BP:				
+		case rn_EBP:
+			return rn_RBP;
+		case rn_SPL:
+		case rn_SP:				
+		case rn_ESP:
+			return rn_RSP;
+		case rn_R8B:
+		case rn_R8W:
+		case rn_R8D:
+			return rn_R8;
+		case rn_R9B:
+		case rn_R9W:
+		case rn_R9D:
+			return rn_R9;
+		case rn_R10B:
+		case rn_R10W:
+		case rn_R10D:
+			return rn_R10;
+		case rn_R11B:
+		case rn_R11W:
+		case rn_R11D:
+			return rn_R11;
+		case rn_R12B:
+		case rn_R12W:
+		case rn_R12D:
+			return rn_R12;
+		case rn_R13B:
+		case rn_R13W:
+		case rn_R13D:
+			return rn_R13;
+		case rn_R14B:
+		case rn_R14W:
+		case rn_R14D:
+			return rn_R14;
+		case rn_R15B:
+		case rn_R15W:
+		case rn_R15D:
+			return rn_R15;
+
+		default:
+			return rn_UNKNOWN;
+			break;
+	}
+}
+
+RegisterID_t IRDB_SDK::convertRegisterTo32bit(const RegisterID_t p_reg)
+{
+	if (is32bitRegister(p_reg))
+		return p_reg;
+
+	switch (p_reg)
+	{
+		case rn_RAX:   return  rn_EAX;
+		case rn_RBX:   return  rn_EBX;
+		case rn_RCX:   return  rn_ECX;
+		case rn_RDX:   return  rn_EDX;
+		case rn_RBP:   return  rn_EBP;
+		case rn_RSP:   return  rn_ESP;
+		case rn_RSI:   return  rn_ESI;
+		case rn_RDI:   return  rn_EDI;
+		case  rn_R8:   return  rn_R8D;
+		case  rn_R9:   return  rn_R9D;
+		case rn_R10:   return rn_R10D;
+		case rn_R11:   return rn_R11D;
+		case rn_R12:   return rn_R12D;
+		case rn_R13:   return rn_R13D;
+		case rn_R14:   return rn_R14D;
+		case rn_R15:   return rn_R15D;
+		default:
+			return rn_UNKNOWN;
+			break;
+	}
+}
+
+RegisterID_t IRDB_SDK::convertRegisterTo16bit(const RegisterID_t p_reg)
+{
+	if (is16bitRegister(p_reg))
+		return p_reg;
+
+	switch (p_reg)
+	{
+		case rn_RAX: case  rn_EAX:   return rn_AX;
+		case rn_RBX: case  rn_EBX:   return rn_BX;
+		case rn_RCX: case  rn_ECX:   return rn_CX;
+		case rn_RDX: case  rn_EDX:   return rn_DX;
+		case rn_RBP: case  rn_EBP:   return rn_BP;
+		case rn_RSP: case  rn_ESP:   return rn_SP;
+		case rn_RSI: case  rn_ESI:   return rn_SI;
+		case rn_RDI: case  rn_EDI:   return rn_DI;
+		case  rn_R8: case  rn_R8D:   return rn_R8W;
+		case  rn_R9: case  rn_R9D:   return rn_R9W;
+		case rn_R10: case rn_R10D:   return rn_R10W;
+		case rn_R11: case rn_R11D:   return rn_R11W;
+		case rn_R12: case rn_R12D:   return rn_R12W;
+		case rn_R13: case rn_R13D:   return rn_R13W;
+		case rn_R14: case rn_R14D:   return rn_R14W;
+		case rn_R15: case rn_R15D:   return rn_R15W;
+		default:
+			return rn_UNKNOWN;
+			break;
+	}
+}
+
diff --git a/irdb-lib/libMEDSannotation/LICENSE.txt b/irdb-lib/libMEDSannotation/LICENSE.txt
new file mode 100644
index 0000000000000000000000000000000000000000..312fba3fce32ba9e8a488ac58885ca41c59c2aa8
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/LICENSE.txt
@@ -0,0 +1,14 @@
+*************************************************************************************
+*
+* Unless otherwise specified, software artifacts in this directory and its
+* subdirectories are subject to:
+*
+* GOVERNMENT PURPOSE RIGHTS
+*
+* The Government's rights to use, modify, reproduce, release, perform, display, or
+* disclose this software are restricted by GOVERNMENT PURPOSE RIGHTS.
+*
+* Any reproduction of the software or portions thereof marked with this legend 
+* must also reproduce the markings.
+*
+*************************************************************************************
diff --git a/irdb-lib/libMEDSannotation/Makefile.in b/irdb-lib/libMEDSannotation/Makefile.in
new file mode 100644
index 0000000000000000000000000000000000000000..f9227c74436aa0f6905cc8f054691394a2db56ac
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/Makefile.in
@@ -0,0 +1,9 @@
+
+CC=@CC@
+CXX=@CXX@
+
+all:
+	cd src;make CC=$(CC) CXX=$(CXX)
+
+clean:
+	cd src; make clean
diff --git a/irdb-lib/libMEDSannotation/SConscript b/irdb-lib/libMEDSannotation/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..cb89f07ae1ff32592f4b06405da21d792395931f
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/SConscript
@@ -0,0 +1,36 @@
+import os
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+lib="MEDSannotation"
+
+files=  '''
+	src/FuncExitAnnotation.cpp
+	src/MEDS_AnnotationParser.cpp
+	src/MEDS_FPTRShadowAnnotation.cpp
+	src/MEDS_DeadRegAnnotation.cpp
+	src/MEDS_FRSafeAnnotation.cpp
+	src/MEDS_FuncPrototypeAnnotation.cpp
+	src/MEDS_InstructionCheckAnnotation.cpp
+	src/MEDS_MemoryRangeAnnotation.cpp
+	src/MEDS_ProblemFuncAnnotation.cpp
+	src/MEDS_Register.cpp
+	src/MEDS_SafeFuncAnnotation.cpp
+	src/VirtualOffset.cpp
+	'''
+cpppath=''' 
+	./include/
+	$IRDB_SDK/include/
+	'''
+
+#CFLAGS="-fPIC  "
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS=" -std=c++11 -Wall -Werror ")
+lib=myenv.SharedLibrary(lib, Split(files))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+Return('install')
diff --git a/irdb-lib/libMEDSannotation/SConstruct b/irdb-lib/libMEDSannotation/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..b3bd01322f2b78089fd86e0e9b0ae01897c9c8a5
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+Return('lib')
diff --git a/irdb-lib/libMEDSannotation/include/FuncExitAnnotation.hpp b/irdb-lib/libMEDSannotation/include/FuncExitAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..39ffd69cf289e282596c115ec76e04ed3d5d3e50
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/FuncExitAnnotation.hpp
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _FUNCEXITANNOTATION_H_
+#define _FUNCEXITANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS  annotation
+//
+class MEDS_FuncExitAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_FuncExitAnnotation() {};
+		MEDS_FuncExitAnnotation(const string &p_rawLine);
+		virtual ~MEDS_FuncExitAnnotation(){}
+
+		virtual const string toString() const { return "tail call: "+m_rawInputLine; }
+
+	private:
+		void init();
+		void parse();
+
+	private:
+		std::string m_rawInputLine;
+};
+
+}
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS.hpp b/irdb-lib/libMEDSannotation/include/MEDS.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..c3b9388027ed400a4f87f290cabde852688f5546
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS.hpp
@@ -0,0 +1,36 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_H
+#define _MEDS_H
+
+namespace MEDS_Annotation
+{
+
+class MEDS
+{
+	public:
+		enum Register { UNKNOWN, EAX, EBX, ECX, EDX };
+};
+
+
+}
+#endif
+
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_AnnotationBase.hpp b/irdb-lib/libMEDSannotation/include/MEDS_AnnotationBase.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..1c1a2cdcd41d1f12350b2a7c1cb8b7719c764780
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_AnnotationBase.hpp
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef MEDS_ANNOTATION_BASE_HPP
+#define MEDS_ANNOTATION_BASE_HPP
+
+
+#include <assert.h>
+#include "VirtualOffset.hpp"
+
+
+namespace MEDS_Annotation
+{
+
+
+// base class for deriving objects.
+class MEDS_AnnotationBase
+{
+	public:			
+		MEDS_AnnotationBase() { init(); }
+		virtual ~MEDS_AnnotationBase()  { }
+
+		/* i'd rather make this a pure virtual func, but can't figure out why it won't compile */
+		virtual const std::string toString() const =0;
+
+		// valid annotation?
+		virtual bool isValid() const { return m_isValid; }
+		virtual void setValid() { m_isValid = true; }
+		virtual void setInvalid() { m_isValid = false; }
+
+		// virtual offset
+		virtual VirtualOffset getVirtualOffset() const { return m_virtualOffset; }
+		virtual void setVirtualOffset(VirtualOffset p_vo) { m_virtualOffset = p_vo; }
+
+		virtual void setInstructionSize(int p_size) { m_size = p_size; }
+		virtual int getInstructionSize() { return m_size; }
+
+		virtual void init() { m_isValid = false; m_size = 0; }
+
+		virtual bool isFuncAnnotation() const { return false; } // false by default 
+
+	protected:
+		bool m_isValid;
+		int m_size;
+		VirtualOffset  m_virtualOffset;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_AnnotationParser.hpp b/irdb-lib/libMEDSannotation/include/MEDS_AnnotationParser.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..a65a88db46f47686f318dd583323bd9eb1d57c51
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_AnnotationParser.hpp
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_ANNOTATION_PARSER_H_
+#define _MEDS_ANNOTATION_PARSER_H_
+
+#include <map>
+#include <iostream>
+
+#include "MEDS_AnnotationBase.hpp"
+#include "VirtualOffset.hpp"
+
+namespace MEDS_Annotation
+{
+
+typedef std::multimap<const VirtualOffset, MEDS_AnnotationBase*> MEDS_Annotations_t;
+typedef std::pair<const VirtualOffset, MEDS_AnnotationBase*> MEDS_Annotations_Pair_t;
+
+typedef std::multimap<const std::string, MEDS_AnnotationBase*> MEDS_FuncAnnotations_t;
+typedef std::pair<const std::string, MEDS_AnnotationBase*> MEDS_Annotations_FuncPair_t;
+
+class MEDS_AnnotationParser
+{
+	public:
+		MEDS_AnnotationParser() {};
+		MEDS_AnnotationParser(std::istream &); 	/* pass opened file */
+		void parseFile(std::istream &);
+		void parseFile(const std::string &);	 /* pass filename */
+		MEDS_Annotations_t &         getAnnotations() { return m_annotations; }
+		MEDS_FuncAnnotations_t & getFuncAnnotations() { return m_func_annotations; }
+
+	private:
+		// helpers
+		template <class type> bool add_if_valid(std::string line);
+
+		// data
+		MEDS_Annotations_t m_annotations;
+		MEDS_FuncAnnotations_t m_func_annotations;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_DeadRegAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_DeadRegAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..087bd687327740b067f75b4b4fda4f3ae98997eb
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_DeadRegAnnotation.hpp
@@ -0,0 +1,62 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_DEADREGSANNOTATION_H_
+#define _MEDS_DEADREGSANNOTATION_H_
+
+#include <algorithm>
+#include <string>
+#include <stdint.h>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+//
+// Class to handle one MEDS limited function pointer shadow annotation
+//
+class MEDS_DeadRegAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_DeadRegAnnotation();
+		MEDS_DeadRegAnnotation(const string& p_rawLine);
+		virtual ~MEDS_DeadRegAnnotation() {}
+		virtual const string toString() const { return "deadregs: " + m_rawInputLine; }
+
+		RegisterSet_t& getRegisterSet() { return regset; }
+
+	private:
+		// base class requirements.
+		void parse();
+
+	private:
+		RegisterSet_t regset;
+		string m_rawInputLine;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_FPTRShadowAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_FPTRShadowAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..b6647248ecc7fa7363eefb5cb39b77f688020a80
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_FPTRShadowAnnotation.hpp
@@ -0,0 +1,97 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_FPTRSHADOWANNOTATION_H_
+#define _MEDS_FPTRSHADOWANNOTATION_H_
+
+#include <algorithm>
+#include <string>
+#include <stdint.h>
+#include "VirtualOffset.hpp"
+#include "MEDS_ShadowAnnotation.hpp"
+#include "MEDS_Register.hpp"
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+#define MEDS_ANNOT_FPTRSHADOW "FPTRSHADOW"
+#define MEDS_ANNOT_FPTRCHECK "FPTRCHECK"
+#define MEDS_ANNOT_ARGSHADOW "ARGSHADOW"
+#define MEDS_ANNOT_ARGCHECK "ARGCHECK"
+
+//
+// Class to handle one MEDS limited function pointer shadow annotation
+//
+// Examples:
+//    8057fa7      3 INSTR FPTRSHADOW  [EAX+8] SHADOWID 5
+//    805829d      3 INSTR FPTRCHECK  [EBP-40] SHADOWID 5
+//    80822aa      7 INSTR FPTRSHADOW  0 SHADOWID 6
+//    80822cc      3 INSTR FPTRSHADOW  EAX SHADOWID 6
+//    8480faa      9 INSTR FPTRSHADOW  4721886 SHADOWID 75
+//
+class MEDS_FPTRShadowAnnotation : public MEDS_ShadowAnnotation
+{
+	public:
+		MEDS_FPTRShadowAnnotation();
+		MEDS_FPTRShadowAnnotation(const string& p_rawLine);
+		virtual ~MEDS_FPTRShadowAnnotation() {}
+		virtual const string toString() const { return "fptr/arg shadow: " + m_rawInputLine; }
+
+		bool isRIPRelative() const;
+		uintptr_t computeRIPAddress();
+		
+                bool isConstant() const;
+                long long getConstantValue(bool&) const;
+
+                bool isRegister() const;
+                bool isMemoryExpression() const;
+
+		const RegisterName getRegister() const;
+		const string& getExpression() const { return m_expression; }
+
+		const bool isFunctionPointerShadow() const { return m_functionPointerShadow; }
+		const bool isCriticalArgumentShadow() const { return m_criticalArgumentShadow; }
+	private:
+		void parse();
+		void setExpression(const string p_expression) { 
+			m_expression = p_expression;
+			std::transform(m_expression.begin(), m_expression.end(), m_expression.begin(), ::tolower);
+		}
+		bool verifyCheckShadowExpression(const string& expression);
+		int parseRegisterOffset(const char*);
+		void parseRegister(const char *p_buf, RegisterName *p_register, int *p_registerOffset);
+
+		void setFunctionPointerShadow(const bool p_val) { m_functionPointerShadow = p_val; }
+		void setCriticalArgumentShadow(const bool p_val) { m_criticalArgumentShadow = p_val; }
+
+	private:
+		string m_rawInputLine;
+		string m_expression;
+		bool m_functionPointerShadow;
+		bool m_criticalArgumentShadow;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_FRSafeAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_FRSafeAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..129cf727c81c862061dcb41e6bebd8e964cf1e9e
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_FRSafeAnnotation.hpp
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_FRSAFEANNOTATION_H_
+#define _MEDS_FRSAFEANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS (integer vulnerability) annotation
+//
+class MEDS_FRSafeAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_FRSafeAnnotation() {};
+		MEDS_FRSafeAnnotation(const string &p_rawLine);
+		virtual ~MEDS_FRSafeAnnotation(){}
+
+		virtual const string toString() const { return "fr safe func: "+m_rawInputLine; }
+
+	private:
+		void init();
+		void parse();
+
+	private:
+		std::string m_rawInputLine;
+};
+
+}
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_FuncAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_FuncAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..e4dc9347c531c14729f85d769f56b08bc729a5eb
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_FuncAnnotation.hpp
@@ -0,0 +1,66 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_FUNCANNOTATION_H_
+#define _MEDS_FUNCANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+// These strings must match those emitted by MEDS in the information annotation file exactly
+#define MEDS_ANNOT_FUNC        "FUNC"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS annotation
+//
+class MEDS_FuncAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_FuncAnnotation() {}
+		virtual ~MEDS_FuncAnnotation(){}
+
+		virtual bool isFuncAnnotation() const { return true; } 
+
+		virtual string getFuncName() const { return m_func_name; }
+		virtual void setFuncName(const string &p_func_name) { m_func_name=p_func_name; }
+
+		virtual bool isLeaf() const { return m_isleaf; }
+		virtual void setLeaf(const bool p_leaf) { m_isleaf = p_leaf; }
+
+		virtual bool hasFramePointer() const { return m_hasfp; }
+		virtual void setHasFramePointer(const bool p_hasfp) { m_hasfp = p_hasfp; }
+
+	private:
+		string m_func_name;
+		bool m_isleaf;
+		bool m_hasfp;
+};
+
+}
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_FuncPrototypeAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_FuncPrototypeAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..4e94a0200ba10799ebfcff7a036119aa536baf45
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_FuncPrototypeAnnotation.hpp
@@ -0,0 +1,120 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_FUNCPROTOTYPEANNOTATION_H_
+#define _MEDS_FUNCPROTOTYPEANNOTATION_H_
+
+#include <string>
+#include <vector>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_FuncAnnotation.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Must match STARS type system
+//    UNINIT = 0,      // Operand type not yet analyzed; type lattice top
+//    NUMERIC = 1,     // Definitely holds non-pointer value (char, int, etc.)
+//    CODEPTR = 2,     // Definitely holds a code address; mmStrata considers this NUMERIC
+//    POINTER = 4,     // Definitely holds a data address
+//    STACKPTR = 8,    // Definitely holds a stack data address (refinement of POINTER)
+//    GLOBALPTR = 16,   // Definitely holds a global static data address (refinement of POINTER)
+//    HEAPPTR = 32,     // Definitely holds a heap data address (refinement of POINTER)
+//    PTROFFSET = 64,   // Offset from a pointer, e.g. a difference between two pointers
+//    NEGATEDPTR = 65,  // Temporary ptr arithmetic leaves NUMERIC-POINTER; should get +POINTER later to make PTROFFSET
+//    UNKNOWN = 96,     // Might hold an address, might not (Bad!); type lattice bottom
+//
+typedef enum {
+	MEDS_TYPE_UNINIT = 0,
+	MEDS_TYPE_NUMERIC = 1, 
+	MEDS_TYPE_CODEPTR = 2,
+	MEDS_TYPE_POINTER = 4, 
+	MEDS_TYPE_STACKPTR = 8, 
+	MEDS_TYPE_GLOBALPTR = 16,
+	MEDS_TYPE_HEAPPTR = 32, 
+	MEDS_TYPE_PTROFFSET = 64,
+	MEDS_TYPE_NEGATEDPTR = 65,
+	MEDS_TYPE_UNKNOWN = 96     
+} MEDS_ArgType;
+
+// wrapper class around MEDS typing system
+class MEDS_Arg {
+	public:
+		MEDS_Arg() { m_type = MEDS_TYPE_UNKNOWN; m_reg = IRDB_SDK::rn_UNKNOWN; }
+		MEDS_Arg(int p_type, RegisterName p_reg = IRDB_SDK::rn_UNKNOWN) { m_type = (MEDS_ArgType) p_type; m_reg = p_reg; }
+		virtual ~MEDS_Arg() {}
+		bool isNumericType() { return m_type == MEDS_TYPE_NUMERIC; }
+		bool isPointerType() { 
+			return m_type == MEDS_TYPE_CODEPTR || m_type == MEDS_TYPE_POINTER || 
+				m_type == MEDS_TYPE_STACKPTR || m_type == MEDS_TYPE_GLOBALPTR || 
+				m_type == MEDS_TYPE_HEAPPTR;
+		}
+		bool isUnknownType() { return !(isNumericType() || isPointerType()); }
+
+	private:
+		MEDS_ArgType m_type;
+		RegisterName m_reg;
+};
+
+//
+// Class to handle one function prototype annotations
+//
+class MEDS_FuncPrototypeAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_FuncPrototypeAnnotation() { init(); };
+		MEDS_FuncPrototypeAnnotation(const string &p_rawLine);
+		virtual ~MEDS_FuncPrototypeAnnotation() {}
+//		virtual bool isFuncPrototypeAnnotation() const { return true; }
+
+		virtual const string toString() const { return "func proto: " + m_rawInputLine; }
+
+		int getNumArgs() const { return m_arguments ? m_arguments->size() : 0; }
+		std::vector<MEDS_Arg>* getArgs() { return m_arguments; }
+		void addArg(MEDS_Arg p_arg) { 
+			if (!m_arguments) m_arguments = new std::vector<MEDS_Arg>;
+			m_arguments->push_back(p_arg);
+		}
+		void setReturnArg(MEDS_Arg p_arg) { 
+			if (!m_returnArg) m_returnArg = new MEDS_Arg;
+			*m_returnArg = p_arg; 
+		}
+		MEDS_Arg* getReturnArg() const { return m_returnArg; }
+
+	private:
+		void init();
+		void parse();
+
+	private:
+		string m_rawInputLine;
+
+		std::vector<MEDS_Arg> *m_arguments;
+		MEDS_Arg *m_returnArg;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_IBAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_IBAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..727bb696a9070dcbcba74fbb008dc63705aae32b
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_IBAnnotation.hpp
@@ -0,0 +1,108 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_IBANNOTATION_H_
+#define _MEDS_IBANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS shadow annotation
+//
+class MEDS_IBAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		typedef enum { SWITCH, RET, UNKNOWN } ib_type_t;
+
+		MEDS_IBAnnotation( const string& p_rawLine) : the_type(UNKNOWN), count(0), complete(false)
+		{ 
+        		setInvalid();
+        		parse(p_rawLine);
+
+		};
+
+		ib_type_t GetType() const  { return the_type; }
+		int GetCount() const { return count; }
+		bool IsComplete() const { return complete; }
+
+		virtual const std::string toString() const
+		{ 
+			std::string ret="IB";
+			if(IsComplete()) ret+=" COMPLETE";
+			ret+=" Count=<na> type=<na>";
+			return ret;
+		}
+
+	protected:
+
+		void parse(const string& p_rawLine)
+		{
+			string tofind="INSTR XREF FROMIB";
+			size_t pos=p_rawLine.find(tofind);
+			if(pos==string::npos)
+				return;
+
+        		VirtualOffset vo(p_rawLine);
+        		m_virtualOffset = vo;
+
+
+			// she be valid
+			setValid();
+
+			tofind="COMPLETE";
+			size_t pos2=p_rawLine.find(tofind);
+			if(pos2!=string::npos)
+			{
+				pos=pos2;
+				complete=true;
+			}
+
+			string rest=p_rawLine.substr(pos+tofind.length());
+			istringstream is(rest);
+			is>>count;	/* get count */
+
+			if(p_rawLine.find("RETURNTARGET")) set_type(RET);
+			if(p_rawLine.find("SWITCHTABLE")) set_type(SWITCH); 
+				
+		}
+
+		void set_type(ib_type_t t)
+		{
+			assert(the_type==UNKNOWN);
+		}
+
+	private:
+
+		ib_type_t the_type;
+		int count;
+		bool complete;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_IBTAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_IBTAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..8fd05f8f0e2ffb4568090e65b037c549abbea9c6
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_IBTAnnotation.hpp
@@ -0,0 +1,129 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBTILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_IBTANNOTATION_H_
+#define _MEDS_IBTANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS shadow annotation
+//
+class MEDS_IBTAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		typedef enum { SWITCH, RET, DATA, UNREACHABLE, ADDRESSED, INDIRCALL, UNKNOWN } ibt_reason_code_t;
+
+		MEDS_IBTAnnotation()=delete;
+		MEDS_IBTAnnotation( const string& p_rawLine) 
+			: xref_addr(0), reason(UNKNOWN)
+		{ 
+        		setInvalid();
+        		parse(p_rawLine);
+
+		};
+
+		ApplicationAddress GetXrefAddr() { return xref_addr; }
+		ibt_reason_code_t GetReason() { return reason; }
+
+		virtual const std::string toString() const
+		{ 
+			return "IBT";
+		}
+
+	protected:
+
+		void parse(const string& p_rawLine)
+		{
+			string tofind="INSTR XREF IBT";
+			size_t pos=p_rawLine.find(tofind);
+			if(pos==string::npos)
+				return;
+
+        		setValid();
+
+                        VirtualOffset vo(p_rawLine);
+                        m_virtualOffset = vo;
+
+
+			stringstream stream(p_rawLine.substr(pos+tofind.length()));
+
+			string from_type;
+			stream >> from_type;
+
+			if(string("FROMIB") == from_type)
+			{
+				stream >> hex >> xref_addr;
+				//cout<<"fromib: '"<<p_rawLine<<"'"<<endl;
+			}
+			else if(string("FROMDATA") == from_type)
+			{
+				stream >> hex >> xref_addr;
+				reason=DATA;
+				//cout<<"fromdata: '"<<p_rawLine<<"'"<<endl;
+				return;
+			}
+			else if(string("FROMUNKNOWN") == from_type)
+			{
+				// no other fields for from UNKNOWN
+				xref_addr=0;
+				//cout<<"fromunknown: '"<<p_rawLine<<"'"<<endl;
+			}
+
+			string reason_code;
+			stream >> reason_code;
+
+			if(string("RETURNTARGET") == reason_code)
+			{ reason=RET; }
+			else if(string("TAILCALLRETURNTARGET") == reason_code)
+			{ reason=RET; }
+			else if(string("SWITCHTABLE") == reason_code)
+			{ reason=SWITCH; }
+			else if(string("UNREACHABLEBLOCK") == reason_code)
+			{ reason=UNREACHABLE; }
+			else if(string("CODEADDRESSTAKEN") == reason_code)
+			{ reason=ADDRESSED; }
+			else if(string("INDIRCALL") == reason_code)
+			{ reason=INDIRCALL; }
+			else
+			{ reason=UNKNOWN; }
+
+			if(reason==UNKNOWN) 
+				cout<<"unknown reason code: '"<<reason_code<<"'"<<endl;
+				
+		}
+
+	private:
+
+		ApplicationAddress xref_addr;
+		ibt_reason_code_t reason;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_InstructionCheckAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_InstructionCheckAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..023cf5776277b0a69246993734e1fa515b407120
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_InstructionCheckAnnotation.hpp
@@ -0,0 +1,152 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_INSTRUCTIONCHECKANNOTATION_H_
+#define _MEDS_INSTRUCTIONCHECKANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+// These strings must match those emitted by MEDS in the information annotation file exactly
+#define MEDS_ANNOT_INSTR        "INSTR"
+#define MEDS_ANNOT_CHECK        "CHECK"
+#define MEDS_ANNOT_OVERFLOW     "OVERFLOW"
+#define MEDS_ANNOT_UNDERFLOW    "UNDERFLOW"
+#define MEDS_ANNOT_SIGNEDNESS   "SIGNEDNESS"
+#define MEDS_ANNOT_TRUNCATION   "TRUNCATION"
+#define MEDS_ANNOT_SIGNED       "SIGNED"
+#define MEDS_ANNOT_UNSIGNED     "UNSIGNED"
+#define MEDS_ANNOT_UNKNOWNSIGN  "UNKNOWNSIGN"
+#define MEDS_ANNOT_NOFLAG       "NOFLAG"
+#define MEDS_ANNOT_INFINITELOOP "INFINITELOOP"
+#define MEDS_ANNOT_SEVERE       "SEVERE"
+#define MEDS_ANNOT_FLOWS_INTO_CRITICAL_SINK  "SINKMALLOC"
+#define MEDS_ANNOT_MEMSET       "MEMSET"
+#define MEDS_ANNOT_IDIOM        "IDIOM"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS (integer vulnerability) annotation
+//
+class MEDS_InstructionCheckAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_InstructionCheckAnnotation();
+		MEDS_InstructionCheckAnnotation(const string &p_rawLine);
+		virtual ~MEDS_InstructionCheckAnnotation(){}
+
+		// integer vulnerability types
+		bool isOverflow() const { return m_isOverflow; }
+		bool isUnderflow() const { return m_isUnderflow; }
+		bool isTruncation() const { return m_isTruncation; }
+		bool isSignedness() const { return m_isSignedness; }
+		bool isSevere() const { return m_isSevere; }
+		void setOverflow() { m_isOverflow = true; }
+
+		// signed vs. unsigned
+		bool isUnsigned() const { return m_isUnsigned; }
+		bool isSigned() const { return m_isSigned; }
+		bool isUnknownSign() const { return m_isUnknownSign; }
+
+		void setSigned() { m_isSigned = true; }
+		void setUnsigned() { m_isUnsigned = true; }
+		void setUnknownSign() { m_isUnknownSign = true; }
+
+		// overflow with no flags, e.g. lea
+		bool isNoFlag() const { return m_isNoFlag; }
+
+        // infinite loop annotation?
+		bool isInfiniteLoop() const { return m_isInfiniteLoop; }
+
+		// memset annotation?
+		bool isMemset() const { return m_isMemset; }
+		bool isEspOffset() const { return m_isEspOffset; }
+		bool isEbpOffset() const { return m_isEbpOffset; }
+		int getStackOffset() const { return m_stackOffset; }
+		int getObjectSize() const { return m_objectSize; }
+
+		// is idiom?
+		bool isIdiom() const { return m_isIdiom; }
+		int getIdiomNumber() const { return m_idiomNumber; }
+		void setIdiomNumber(int number) { m_idiomNumber = number; }
+
+		// get bitwidth
+		int getBitWidth() const { return m_bitWidth; }
+		void setBitWidth(int p_bitWidth) { m_bitWidth = p_bitWidth; }
+		int getTruncationFromWidth() const { return m_truncationFromWidth; }
+		int getTruncationToWidth() const { return m_truncationToWidth; }
+
+		// get register
+		MEDS_Annotation::RegisterName getRegister() const { return m_register; }
+		MEDS_Annotation::RegisterName getRegister2() const { return m_register2; }
+
+		const string getTarget() const { return m_target; }
+		const string getTarget2() const { return m_target2; }
+
+		const string toString() const { return m_rawInputLine; }
+
+		// data flow
+		// @todo: expand the set, allow getter functions to retrieve name of sink
+		bool flowsIntoCriticalSink() const { return m_flowsIntoCriticalSink; }
+
+	private:
+		void init();
+		void parse();
+
+	private:
+		string         m_rawInputLine;
+		bool           m_isOverflow;
+		bool           m_isUnderflow;
+		bool           m_isSignedness;
+		bool           m_isTruncation;
+		bool           m_isSigned;
+		bool           m_isUnsigned;
+		bool           m_isUnknownSign;
+		bool           m_isNoFlag;
+		bool           m_isInfiniteLoop;
+		bool           m_isMemset;
+		bool           m_isSevere;
+		int            m_bitWidth;
+		int            m_truncationFromWidth;
+		int            m_truncationToWidth;
+		bool           m_isEspOffset;
+		bool           m_isEbpOffset;
+		int            m_stackOffset;
+		int            m_objectSize;
+		bool           m_isValid;
+		bool           m_flowsIntoCriticalSink;
+		bool           m_isIdiom;
+		int            m_idiomNumber;
+		MEDS_Annotation::RegisterName       m_register;
+		MEDS_Annotation::RegisterName       m_register2;
+		string         m_target;
+		string         m_target2;
+};
+
+}
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_MemoryRangeAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_MemoryRangeAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..3dd234fe9e6f4ebb55d6369730b08abea05d475c
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_MemoryRangeAnnotation.hpp
@@ -0,0 +1,121 @@
+/*
+ * Copyright (c) 2018 - University of Virginia
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.edu
+ *
+ */
+
+#ifndef _MEDS_MEMORYRANGEANNOTATION_H_
+#define _MEDS_MEMORYRANGEANNOTATION_H_
+
+#include <algorithm>
+#include <string>
+#include <stdint.h>
+#include "VirtualOffset.hpp"
+#include "MEDS_ShadowAnnotation.hpp"
+#include "MEDS_Register.hpp"
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+#define MEDS_ANNOT_STATICMEMWRITE "STATICMEMWRITE"
+#define MEDS_ANNOT_STACKMEMRANGE "STACKMEMRANGE"
+#define MEDS_ANNOT_SENTINEL "SENTINEL"
+
+//
+// Class to handle one MEDS memory range annotation
+//
+// Examples:
+//    417748     12 INSTR STATICMEMWRITE MIN 3c60320  LIMIT 4e53730  ZZ
+//     Meaning: instruction at 0x417748 is 12 bytes in length and writes to
+//      a static memory data scoop includes the MIN address 0x3c60320.
+//      The LIMIT address 0x4e53730 is beyond the range written to by
+//      this instruction. The assembly language instruction is:
+//
+//      mov 0x3c3d630[RAX + RDX*8], 0 ; zero out buffer in 434.zeusmp
+//
+//      Note that 0x3c3d630 in the assembly language could trick an
+//      IRDB transform, such as the move_globals defense, into thinking
+//      that the instruction writes to the data scoop containing address
+//      0x3c3d630, when in fact the initial value of register RDX is large
+//      enough to push the initial memory address up to 0x3c60320, which is
+//      a different data scoop in global static memory. The annotation provides
+//      enough info to associate the instruction with the data scoop written.
+//
+//    4992ea      4 INSTR STACKMEMRANGE MIN RSP-568 LIMIT RSP-48 INSTRSPDELTA -592 ZZ
+//     Meaning: instruction at 0x4992ea is 4 bytes in length and writes
+//      to a stack memory location from RSP-568 to just below RSP-48, where
+//      the stack offsets are relative to the value of the stack pointer on
+//      function entry. The stack pointer has a current value at this instruction
+//      that is -592 from the function entry value. This means that the instruction
+//      writes a minimum of 24 bytes higher than the current stack pointer value.
+//      The assembly language instruction is:
+//
+//      mov 0x8[R8],RCX   ; store RCX into [R8]+8 in busybox.psexe
+//
+//      It is not apparent from the assembly language that stack memory is involved,
+//      but STARS loop analysis and symbolic analysis have determined that the memory
+//      write is to the range [MIN..LIMIT-1] as seen in the annotation.
+//
+//    4992ea      4 INSTR SENTINEL BASE 43d920 OFFSET -8 ZZ
+//     Meaning: Address (BASE + OFFSET) is used as a loop sentinel in instruction at 0x4992ea.
+//     The loop only accesses memory at BASE, so the address of BASE should be used
+//     as the data scoop referred to by this instruction, e.g. cmp rax,0x43d918 could be
+//     the instruction, followed by jg top_of_loop. When RAX reaches value 0x43d918, the loop
+//     exits without using that value except as a sentinel to terminate the loop. 0x43d918 is
+//     in a different data scoop than 0x43d920, and 0x43d920 is the relevant scoop for the loop.
+//
+
+class MEDS_MemoryRangeAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_MemoryRangeAnnotation();
+		MEDS_MemoryRangeAnnotation(const string& p_rawLine);
+		virtual ~MEDS_MemoryRangeAnnotation() {};
+		virtual const string toString() const { return "Memory Range: " + m_rawInputLine; };
+
+		uint64_t getRangeMin() const { return m_rangeMin; };
+		uint64_t getRangeLimit() const { return m_rangeLimit; };
+		int64_t getSentinelOffset() const { return m_sentinelOffset; };
+
+		const bool isStackRange() const { return m_stackRange; };
+		const bool isStaticGlobalRange() const { return m_staticGlobalRange; };
+		const bool isSentinel() const { return m_sentinel; };
+
+	private:  // methods
+		void parse();
+		void setStackRange(const bool p_val) { m_stackRange = p_val; };
+		void setStaticGlobalRange(const bool p_val) { m_staticGlobalRange = p_val; };
+		void setSentinel(const bool p_val) { m_sentinel = p_val; };
+		void setRangeMin(const uint64_t p_val) { m_rangeMin = p_val; };
+		void setRangeLimit(const uint64_t p_val) { m_rangeLimit = p_val; };
+		void setSentinelOffset(const int64_t p_val) { m_sentinelOffset = p_val; };
+
+	private: // data
+		string m_rawInputLine;
+		bool m_stackRange;
+		bool m_staticGlobalRange;
+		bool m_sentinel;
+		uint64_t m_rangeMin;
+		uint64_t m_rangeLimit;
+		int64_t m_sentinelOffset;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_ProblemFuncAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_ProblemFuncAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..1bf520be751f63742aab39137b0656b8c042068b
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_ProblemFuncAnnotation.hpp
@@ -0,0 +1,75 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_PROBLEMFUNCANNOTATION_H_
+#define _MEDS_PROBLEMFUNCANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_FuncAnnotation.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+// These strings must match those emitted by MEDS in the information annotation file exactly
+#define MEDS_ANNOT_FUNC        "FUNC"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS (integer vulnerability) annotation
+//
+class MEDS_ProblemFuncAnnotation : public MEDS_FuncAnnotation
+{
+
+	public:
+		enum ProblemType { pt_CallUnresolved, pt_JumpUnresolved, pt_BadStackAnalysis, pt_BadRTLs, pt_Unknown };
+
+		MEDS_ProblemFuncAnnotation() {};
+		MEDS_ProblemFuncAnnotation(const string &p_rawLine);
+		virtual ~MEDS_ProblemFuncAnnotation(){}
+
+		virtual const string toString() const { return "problem func: "+m_rawInputLine; }
+
+		virtual void markCallUnresolved() { pt = pt_CallUnresolved; setValid(); }
+		virtual void markJumpUnresolved() { pt = pt_JumpUnresolved; setValid(); }
+		virtual bool isCallUnresolved() { return pt==pt_CallUnresolved; }
+		virtual bool isJumpUnresolved() { return pt==pt_JumpUnresolved; }
+
+		ProblemType getProblemType() { return pt; }
+		void setProblemType( ProblemType _pt) { pt=_pt; }
+
+	private:
+		void init();
+		void parse();
+		void matches(std::string line, string pattern, ProblemType prob_type);
+
+	private:
+		std::string m_rawInputLine;
+
+		ProblemType pt;
+
+};
+
+}
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_Register.hpp b/irdb-lib/libMEDSannotation/include/MEDS_Register.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..c1207a0608112e35dfa5a5bab123aed9f4f08ea6
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_Register.hpp
@@ -0,0 +1,79 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_REGISTER_H
+#define _MEDS_REGISTER_H
+
+#include <string>
+#include <set>
+#include <irdb-util>
+#include <irdb-deep>
+
+namespace MEDS_Annotation 
+{
+
+
+#if 0
+enum RegisterName 
+{
+	IRDB_SDK::rn_UNKNOWN, 
+	IRDB_SDK::rn_EFLAGS, 
+	IRDB_SDK::rn_RIP,
+	IRDB_SDK::rn_EAX, IRDB_SDK::rn_EBX, IRDB_SDK::rn_ECX, IRDB_SDK::rn_EDX, IRDB_SDK::rn_ESI, IRDB_SDK::rn_EDI, IRDB_SDK::rn_EBP, IRDB_SDK::rn_ESP, IRDB_SDK::rn_R8D, IRDB_SDK::rn_R9D, IRDB_SDK::rn_R10D, IRDB_SDK::rn_R11D, IRDB_SDK::rn_R12D, IRDB_SDK::rn_R13D, IRDB_SDK::rn_R14D, IRDB_SDK::rn_R15D, 
+	IRDB_SDK::rn_RAX, IRDB_SDK::rn_RBX, IRDB_SDK::rn_RCX, IRDB_SDK::rn_RDX, IRDB_SDK::rn_RBP, IRDB_SDK::rn_RSP, IRDB_SDK::rn_RSI, IRDB_SDK::rn_RDI, IRDB_SDK::rn_R8,  IRDB_SDK::rn_R9,  IRDB_SDK::rn_R10,  IRDB_SDK::rn_R11,  IRDB_SDK::rn_R12,  IRDB_SDK::rn_R13,  IRDB_SDK::rn_R14,  IRDB_SDK::rn_R15, 
+	IRDB_SDK::rn_AX, IRDB_SDK::rn_BX, IRDB_SDK::rn_CX, IRDB_SDK::rn_DX, IRDB_SDK::rn_BP, IRDB_SDK::rn_SP, IRDB_SDK::rn_SI, IRDB_SDK::rn_DI, IRDB_SDK::rn_R8W, IRDB_SDK::rn_R9W, IRDB_SDK::rn_R10W, IRDB_SDK::rn_R11W, IRDB_SDK::rn_R12W, IRDB_SDK::rn_R13W, IRDB_SDK::rn_R14W, IRDB_SDK::rn_R15W, 
+	IRDB_SDK::rn_AH, IRDB_SDK::rn_BH, IRDB_SDK::rn_CH, IRDB_SDK::rn_DH, IRDB_SDK::rn_SIH, IRDB_SDK::rn_DIH, IRDB_SDK::rn_BPH, IRDB_SDK::rn_SPH, /* 'H' versions of regs only exist for lower 8 regs */ 
+	IRDB_SDK::rn_AL, IRDB_SDK::rn_BL, IRDB_SDK::rn_CL, IRDB_SDK::rn_DL, IRDB_SDK::rn_SIL, IRDB_SDK::rn_DIL, IRDB_SDK::rn_BPL, IRDB_SDK::rn_SPL, IRDB_SDK::rn_R8B, IRDB_SDK::rn_R9B, IRDB_SDK::rn_R10B, IRDB_SDK::rn_R11B, IRDB_SDK::rn_R12B, IRDB_SDK::rn_R13B, IRDB_SDK::rn_R14B, IRDB_SDK::rn_R15B, 
+};
+
+typedef std::set<RegisterName> RegisterSet_t;
+#endif
+using RegisterName   = IRDB_SDK::RegisterID;
+using RegisterName_t = IRDB_SDK::RegisterID_t;
+using RegisterSet_t  = IRDB_SDK::RegisterIDSet_t;
+
+
+
+
+class Register 
+{
+
+	public:
+  		static RegisterName getRegister(std::string);
+  		static RegisterName getRegister(char *str);
+  		static bool isValidRegister(std::string);
+  		static bool isValidRegister(const RegisterName);
+  		static bool is64bit(RegisterName);
+  		static bool is32bit(RegisterName);
+  		static bool is16bit(RegisterName);
+  		static bool is8bit(RegisterName);
+  		static int getBitWidth(RegisterName);
+  		static std::string toString(RegisterName);
+  		static RegisterName getFreeRegister64(const RegisterSet_t &p_used);
+  		static std::string readRegisterSet(const std::string &in, RegisterSet_t &out);
+		static RegisterName promoteTo64(const RegisterName p_reg);
+		static RegisterName demoteTo32(const RegisterName p_reg);
+		static RegisterName demoteTo16(const RegisterName p_reg);
+
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_SafeFuncAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_SafeFuncAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..835233166c99620d0fd5daa74dc654420aebbce2
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_SafeFuncAnnotation.hpp
@@ -0,0 +1,67 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_SAFEFUNCANNOTATION_H_
+#define _MEDS_SAFEFUNCANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_FuncAnnotation.hpp"
+
+
+namespace MEDS_Annotation 
+{
+
+// These strings must match those emitted by MEDS in the information annotation file exactly
+#define MEDS_ANNOT_FUNC        "FUNC"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS (integer vulnerability) annotation
+//
+class MEDS_SafeFuncAnnotation : public MEDS_FuncAnnotation
+{
+	public:
+		MEDS_SafeFuncAnnotation() {m_safe_func=false;}
+		MEDS_SafeFuncAnnotation(const string &p_rawLine);
+		virtual ~MEDS_SafeFuncAnnotation(){}
+
+		virtual const string toString() const { return "safe func: "+m_rawInputLine; }
+
+		virtual void markSafe() { m_safe_func = true; setValid(); }
+		virtual void markUnsafe() { m_safe_func = false; setValid(); }
+		virtual bool isSafe() { return m_safe_func; }
+
+
+	private:
+		void init();
+		void parse();
+
+	private:
+		std::string m_rawInputLine;
+
+		bool m_safe_func;
+};
+
+}
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_ShadowAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_ShadowAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..7a987d98cc3d49dc7c6ea0a429f60c441c367dd1
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_ShadowAnnotation.hpp
@@ -0,0 +1,64 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_SHADOWANNOTATION_H_
+#define _MEDS_SHADOWANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_AnnotationBase.hpp"
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS shadow annotation
+//
+class MEDS_ShadowAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		MEDS_ShadowAnnotation() {
+			m_shadowDefine = false;
+			m_shadowCheck = false; 
+			m_shadowId = -1; 
+		};
+		virtual ~MEDS_ShadowAnnotation() {}
+	
+		const bool isDefineShadowId() const { return m_shadowDefine; }
+		const bool isCheckShadowId() const { return m_shadowCheck; }
+		const int getShadowId() const { return m_shadowId; }
+
+	protected:
+		void setDefineShadowId() { m_shadowDefine = true; }
+		void setCheckShadowId() { m_shadowCheck = true; }
+		void setShadowId(int p_id) { m_shadowId = p_id; }
+
+	private:
+		bool m_shadowDefine;
+		bool m_shadowCheck;
+		int  m_shadowId;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/MEDS_TakesAddressAnnotation.hpp b/irdb-lib/libMEDSannotation/include/MEDS_TakesAddressAnnotation.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..524b100ac030bfbba02a15512540e9912d792029
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/MEDS_TakesAddressAnnotation.hpp
@@ -0,0 +1,99 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _MEDS_TAKENADDRESSANNOTATION_H_
+#define _MEDS_TAKENADDRESSANNOTATION_H_
+
+#include <string>
+#include "VirtualOffset.hpp"
+#include "MEDS_AnnotationBase.hpp"
+#include <iostream>
+
+namespace MEDS_Annotation 
+{
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+//
+// Class to handle one MEDS shadow annotation
+//
+class MEDS_TakesAddressAnnotation : public MEDS_AnnotationBase
+{
+	public:
+		typedef enum { SWITCH, RET, UNKNOWN } ib_type_t;
+
+		MEDS_TakesAddressAnnotation( const string& p_rawLine) : 
+			referenced_address(0),
+			m_isCode(false)
+		{ 
+        		setInvalid();
+        		parse(p_rawLine);
+
+		};
+
+
+		virtual const std::string toString() const
+		{ 
+			std::string ret="TakesAddress="+to_string(referenced_address);
+			return ret;
+		}
+
+		ApplicationAddress GetReferencedAddress() const { return referenced_address; }
+		bool isCode() const { return m_isCode; }
+		bool isData() const { return !m_isCode; }
+
+	protected:
+
+		void parse(const string& p_rawLine)
+		{
+			const auto tofind=string("INSTR XREF TAKES_ADDRESS_OF ");
+			const auto codestring=string("CODE");
+			const auto pos=p_rawLine.find(tofind);
+			if(pos==string::npos)
+				return;
+
+			// she be valid
+			setValid();
+
+			m_isCode=(p_rawLine.find(codestring)!=string::npos);
+        		m_virtualOffset = VirtualOffset(p_rawLine);
+
+			// skips over INSTR*{code|data}
+			const auto rest=p_rawLine.substr(pos+tofind.length()+codestring.length());
+			istringstream is(rest);
+			is >> hex >>referenced_address;	/* get the address */
+
+			// cout<<"Found takes_address of "<<m_virtualOffset.to_string() << " to " 
+			//    << hex << referenced_address<< " from '" << rest << "'"<<endl;
+
+				
+		}
+
+
+	private:
+
+		ApplicationAddress referenced_address;
+		bool m_isCode;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/VirtualOffset.hpp b/irdb-lib/libMEDSannotation/include/VirtualOffset.hpp
new file mode 100644
index 0000000000000000000000000000000000000000..cabc12f221cbe13f9e8744bbb0e02468894f1a47
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/VirtualOffset.hpp
@@ -0,0 +1,59 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _VIRTUAL_OFFSET_H_
+#define _VIRTUAL_OFFSET_H_
+
+#include <string>
+#include <sstream>
+
+namespace MEDS_Annotation
+{
+
+typedef unsigned long long ApplicationAddress;
+
+#define DEFAULT_LIBRARY_NAME "a.out"
+
+class VirtualOffset 
+{
+	public:
+		VirtualOffset();
+		VirtualOffset(const std::string &p_offset, const std::string &p_libraryName);
+		VirtualOffset(const std::string &p_offset);
+		VirtualOffset(const int p_offset);
+
+		ApplicationAddress getOffset() const;
+		std::string getLibraryName() const;
+
+		bool operator < (const VirtualOffset &p_other) const;
+		bool operator == (const VirtualOffset &p_other) const;
+		VirtualOffset& operator = (const VirtualOffset &p_other);
+
+		const std::string to_string() const { std::ostringstream oss; oss<<getLibraryName() << "+0x"<<std::hex<<getOffset(); return oss.str(); }
+		const std::string toString() const { return to_string(); }
+
+	private:
+		ApplicationAddress   m_offset;
+		std::string          m_libraryName;
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/include/libMEDSAnnotation.h b/irdb-lib/libMEDSannotation/include/libMEDSAnnotation.h
new file mode 100644
index 0000000000000000000000000000000000000000..a4f17f37c494c7f2e0d8b5279b617ecc553999e0
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/include/libMEDSAnnotation.h
@@ -0,0 +1,24 @@
+#ifndef LIBMEDSAnnotation_h
+#define LIBMEDSAnnotation_h
+
+#include "FuncExitAnnotation.hpp"
+#include "MEDS_AnnotationBase.hpp"
+#include "MEDS_AnnotationParser.hpp"
+#include "MEDS_DeadRegAnnotation.hpp"
+#include "MEDS_FPTRShadowAnnotation.hpp"
+#include "MEDS_FRSafeAnnotation.hpp"
+#include "MEDS_FuncAnnotation.hpp"
+#include "MEDS_FuncPrototypeAnnotation.hpp"
+#include "MEDS.hpp"
+#include "MEDS_TakesAddressAnnotation.hpp"
+#include "MEDS_IBAnnotation.hpp"
+#include "MEDS_IBAnnotation.hpp"
+#include "MEDS_IBTAnnotation.hpp"
+#include "MEDS_InstructionCheckAnnotation.hpp"
+#include "MEDS_ProblemFuncAnnotation.hpp"
+#include "MEDS_Register.hpp"
+#include "MEDS_SafeFuncAnnotation.hpp"
+#include "MEDS_ShadowAnnotation.hpp"
+#include "VirtualOffset.hpp"
+
+#endif
diff --git a/irdb-lib/libMEDSannotation/src/FuncExitAnnotation.cpp b/irdb-lib/libMEDSannotation/src/FuncExitAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..5f5662cff565181511cd1177cd7a911ef3dc354f
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/FuncExitAnnotation.cpp
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+
+#include "MEDS_Register.hpp"
+#include "FuncExitAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+
+
+
+MEDS_FuncExitAnnotation::MEDS_FuncExitAnnotation(const string &p_rawLine)
+{
+	init();
+	m_rawInputLine=p_rawLine;
+	parse();
+}
+
+void MEDS_FuncExitAnnotation::init()
+{
+}
+
+
+/*
+	Example format -- subject to change:
+   804925b      5 INSTR CALL TAILCALL jmp     check_one_fd
+
+
+*/
+void MEDS_FuncExitAnnotation::parse()
+{
+
+	if (m_rawInputLine.find(" INSTR ")==string::npos)
+                return;
+
+        if (
+		m_rawInputLine.find(" INSTR RETURN ")==string::npos  &&
+		m_rawInputLine.find(" INSTR CALL TAILCALL ")==string::npos 
+	   )
+	{
+		/* INSTR  that's not for a safe fast return */
+		return;
+	}
+
+        // get offset
+        VirtualOffset vo(m_rawInputLine);
+        m_virtualOffset = vo;
+
+	setValid();	// no additional info recorded for right now.
+
+//	if(getenv("VERBOSE")!=NULL)
+		cout<<"Found TAILCALL annotation for "<<vo.to_string()<<endl;
+
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_AnnotationParser.cpp b/irdb-lib/libMEDSannotation/src/MEDS_AnnotationParser.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..85e85a2e4cba5465bf6f576786d1e5c518754329
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_AnnotationParser.cpp
@@ -0,0 +1,111 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <string>
+#include <fstream>
+
+#include "MEDS_AnnotationParser.hpp"
+#include "MEDS_InstructionCheckAnnotation.hpp"
+#include "FuncExitAnnotation.hpp"
+#include "MEDS_FuncPrototypeAnnotation.hpp"
+#include "MEDS_SafeFuncAnnotation.hpp"
+#include "MEDS_ProblemFuncAnnotation.hpp"
+#include "MEDS_FRSafeAnnotation.hpp"
+#include "MEDS_FPTRShadowAnnotation.hpp"
+#include "MEDS_DeadRegAnnotation.hpp"
+#include "MEDS_TakesAddressAnnotation.hpp"
+#include "MEDS_IBAnnotation.hpp"
+#include "MEDS_IBTAnnotation.hpp"
+#include "MEDS_MemoryRangeAnnotation.hpp"
+
+// @todo: multiple annotation per instruction
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+MEDS_AnnotationParser::MEDS_AnnotationParser(istream &p_inputStream)
+{
+	parseFile(p_inputStream);
+}
+
+void MEDS_AnnotationParser::parseFile(const std::string &input_filename)
+{
+	ifstream infile(input_filename.c_str(), ifstream::in);
+
+	if(!infile.is_open())
+		throw string("File not found");
+
+	parseFile(infile);
+}
+
+
+
+template <class type> bool MEDS_AnnotationParser::add_if_valid(string line) 
+{
+	type * annot=new type(line); 
+	if (annot->isValid()) 
+	{ 
+		// note that this should _NOT_ be an if/else for every possible Annotation
+		// this _should_ list the major categorizations of annotations
+		// currently we have annotations that can be looked up by VirtualOffset and looked up by Function
+		if(annot->isFuncAnnotation()) 
+		{ 
+			MEDS_FuncAnnotation* fannot=dynamic_cast<MEDS_FuncAnnotation*>(annot); 
+			assert(fannot); 
+			string nam=fannot->getFuncName(); 
+			m_func_annotations.insert(MEDS_Annotations_FuncPair_t(nam, annot)); 
+		} 
+		else 
+		{ 
+			VirtualOffset vo = annot->getVirtualOffset(); 
+			m_annotations.insert(MEDS_Annotations_Pair_t(vo, annot)); 
+		} 
+		return true;
+	} 
+	else 
+	{ 
+		delete annot; 
+		return false;
+	} 
+}
+
+void MEDS_AnnotationParser::parseFile(istream &p_inputStream)
+{
+	while (!p_inputStream.eof())
+	{
+		auto line=string();
+		getline(p_inputStream, line);
+		if (line.empty()) continue;
+
+		if(add_if_valid<MEDS_DeadRegAnnotation>          (line)) continue;
+		if(add_if_valid<MEDS_FPTRShadowAnnotation>       (line)) continue;
+		if(add_if_valid<MEDS_InstructionCheckAnnotation> (line)) continue;
+		if(add_if_valid<MEDS_FuncPrototypeAnnotation>    (line)) continue;
+		if(add_if_valid<MEDS_SafeFuncAnnotation>         (line)) continue;
+		if(add_if_valid<MEDS_ProblemFuncAnnotation>      (line)) continue;
+		if(add_if_valid<MEDS_FRSafeAnnotation>           (line)) continue;
+		if(add_if_valid<MEDS_FuncExitAnnotation>         (line)) continue;
+		if(add_if_valid<MEDS_TakesAddressAnnotation>     (line)) continue;
+		if(add_if_valid<MEDS_IBAnnotation>               (line)) continue;
+		if(add_if_valid<MEDS_IBTAnnotation>              (line)) continue;
+		if(add_if_valid<MEDS_MemoryRangeAnnotation>      (line)) continue;
+	}
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_DeadRegAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_DeadRegAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..cf2c43872262206ecccfb830555792a331d9d95a
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_DeadRegAnnotation.cpp
@@ -0,0 +1,74 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+
+#include "MEDS_DeadRegAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+/* 
+example:
+
+            4010f0      4 INSTR DEADREGS  EFLAGS RAX ZZ sub     rsp, 8          ; _init
+
+ need to parse out eflags, and rax into the regset variable.
+
+
+*/
+
+MEDS_DeadRegAnnotation::MEDS_DeadRegAnnotation() 
+{
+	setInvalid();	
+}
+
+MEDS_DeadRegAnnotation::MEDS_DeadRegAnnotation(const string &p_rawLine) 
+{
+	setInvalid();	
+	m_rawInputLine=p_rawLine;
+	parse();
+}
+
+void MEDS_DeadRegAnnotation::parse()
+{
+	string tofind=" INSTR DEADREGS ";
+	size_t pos=m_rawInputLine.find(tofind);
+	if (pos==string::npos)
+		return;
+
+        // get offset
+        VirtualOffset vo(m_rawInputLine);
+        m_virtualOffset = vo;
+
+        if (getenv("DEADREGS_VERBOSE")) {
+         	cout <<"Found deadreg annotation in: "<<m_rawInputLine<<endl;
+        }
+	// ignore result of getRegisterSet method because 
+	// we don't need to parse the rest of the line.
+	Register::readRegisterSet(m_rawInputLine.substr(pos+tofind.length()), regset);
+	setValid();	
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_FPTRShadowAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_FPTRShadowAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..017efc30d20ffcaf09ba08b78f9a08e224043bac
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_FPTRShadowAnnotation.cpp
@@ -0,0 +1,284 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+
+#include "MEDS_FPTRShadowAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+/*
+	Example format -- subject to change:
+
+   804b3a6      5 INSTR FPTRSHADOW  [rsp+12] SHADOWID 7
+   804c941      5 INSTR FPTRCHECK  [rsp+12] SHADOWID 7
+   804c945      5 INSTR FPTRCHECK  [rsp] SHADOWID 8
+
+   0x4006ca   7    INSTR FPTRSHADOW  {memory addressing expression} SHADOWID <id>
+
+0x80487a0[RBX]
+0x8047aa0[RBX+RCX]
+0x8098f80[RAX+RDX*2] (NOTE: could be *4 or *8 instead of *2)
+[RBX+RDX*4]
+[RAX+RCX*8+12]
+[RDX+RAX*2-64]
+[R8+R15]
+[R9+R11+48]
+[R13+72]
+[R12*4]
+[R14*2-12]
+
+           805829d      3 INSTR FPTRCHECK  [EBP-40] SHADOWID 5
+           8057fa7      3 INSTR FPTRSHADOW  [EAX+8] SHADOWID 5
+           80822aa      7 INSTR FPTRSHADOW  0 SHADOWID 6
+           80822cc      3 INSTR FPTRSHADOW  EAX SHADOWID 6
+           480faa      9 INSTR FPTRSHADOW  4721886 SHADOWID 75
+*/
+
+MEDS_FPTRShadowAnnotation::MEDS_FPTRShadowAnnotation() : MEDS_ShadowAnnotation()
+{
+	setInvalid();	
+	setCriticalArgumentShadow(false);
+	setFunctionPointerShadow(false);
+}
+
+MEDS_FPTRShadowAnnotation::MEDS_FPTRShadowAnnotation(const string &p_rawLine) : MEDS_ShadowAnnotation()
+{
+	setInvalid();	
+	setCriticalArgumentShadow(false);
+	setFunctionPointerShadow(false);
+	m_rawInputLine=p_rawLine;
+	parse();
+}
+
+void MEDS_FPTRShadowAnnotation::parse()
+{
+	if (m_rawInputLine.find(" INSTR ")==string::npos)
+		return;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_FPTRSHADOW)!=string::npos)
+	{
+		setFunctionPointerShadow(true);
+		setDefineShadowId();
+	}
+
+	if (m_rawInputLine.find(MEDS_ANNOT_ARGSHADOW)!=string::npos)
+	{
+		setCriticalArgumentShadow(true);
+		setDefineShadowId();
+	}
+
+	if (m_rawInputLine.find(MEDS_ANNOT_FPTRCHECK)!=string::npos)
+	{
+		setFunctionPointerShadow(true);
+		setCheckShadowId();
+	}
+
+	if (m_rawInputLine.find(MEDS_ANNOT_ARGCHECK)!=string::npos)
+	{
+		setCriticalArgumentShadow(true);
+		setCheckShadowId();
+	}
+
+	if (!isDefineShadowId() && !isCheckShadowId())
+	{
+		/* invalid annotation */
+		setInvalid();	
+		return;
+	}
+
+	// get offset
+	VirtualOffset vo(m_rawInputLine);
+	setVirtualOffset(vo);
+
+	int shadowId;
+	char buf[2048] = "";
+	int instrSize;
+
+	// 804b3a6      5 INSTR FPTRSHADOW  [esp+12] SHADOWID 7
+	// 804c941      5 INSTR FPTRCHECK  [rdx] SHADOWID 7
+	sscanf(m_rawInputLine.c_str(), "%*x %d %*s %*s %s SHADOWID %d", &instrSize, buf, &shadowId);
+
+	setInstructionSize(instrSize);
+	setExpression(std::string(buf));
+	setShadowId(shadowId);
+
+	cout << "virtual offset: " << hex << getVirtualOffset().getOffset() << dec << endl;
+	cout << "size: " << getInstructionSize() << endl;
+	cout << "expr: " << getExpression() << endl;
+	cout << "shadow id: " << getShadowId() << endl;
+
+	if (shadowId < 0)
+	{
+		setInvalid();
+		cout << "invalid shadow id" << endl;
+		return;
+	}
+
+	if (isCheckShadowId())
+	{
+		cout << "is check shadow id" << endl;
+		if (!verifyCheckShadowExpression(getExpression()))
+		{					
+			setInvalid();
+			cout << "invalid expression" << endl;
+			return;
+		}
+	}
+
+	cout << "valid annotation" << endl;
+	setValid();	
+}
+
+// 8057fa7      3 INSTR FPTRSHADOW  [EAX+8] SHADOWID 5
+// 80822aa      7 INSTR FPTRSHADOW  0 SHADOWID 6
+// 80822cc      3 INSTR FPTRSHADOW  EAX SHADOWID 6
+// 8480faa      9 INSTR FPTRSHADOW  4721886 SHADOWID 75
+bool MEDS_FPTRShadowAnnotation::verifyCheckShadowExpression(const string& expression)
+{
+	return isMemoryExpression() || isRegister() || isConstant();
+}
+
+//           80822aa      7 INSTR FPTRSHADOW  0 SHADOWID 6
+bool MEDS_FPTRShadowAnnotation::isConstant() const
+{
+	if (isRegister() || isMemoryExpression()) return false;
+
+	long long val = 0;
+	std::stringstream ss(getExpression());
+	ss >> val;
+	return !ss.bad();
+}
+
+long long MEDS_FPTRShadowAnnotation::getConstantValue(bool &p_valid) const
+{
+	p_valid = false;
+	if (!isConstant())
+		return 0;
+
+	long long val = 0;
+	std::stringstream ss(getExpression());
+	ss >> val;
+	p_valid = !ss.bad();
+	return val;
+}
+
+// 80822cc      3 INSTR FPTRSHADOW  EAX SHADOWID 6
+bool MEDS_FPTRShadowAnnotation::isRegister() const
+{
+	return Register::getRegister(getExpression()) != IRDB_SDK::rn_UNKNOWN;
+}
+
+// 805829d      3 INSTR FPTRCHECK  [EBP-40] SHADOWID 5
+bool MEDS_FPTRShadowAnnotation::isMemoryExpression() const
+{
+	return (m_expression.find('[') != std::string::npos &&
+	    m_expression.find(']') != std::string::npos);
+}
+
+const RegisterName MEDS_FPTRShadowAnnotation::getRegister() const
+{
+	if (isRegister())
+	{
+		return Register::getRegister(getExpression());
+	}
+	else
+	{
+		return IRDB_SDK::rn_UNKNOWN;
+	}
+}
+
+bool MEDS_FPTRShadowAnnotation::isRIPRelative() const
+{
+	return m_expression.find("rip") != string::npos;
+}
+
+// expect of the form:
+//     [rip+constant]
+//     [rip-constant]
+uintptr_t MEDS_FPTRShadowAnnotation::computeRIPAddress()
+{
+	RegisterName reg=RegisterName();
+	int offset=0;
+
+	parseRegister(getExpression().c_str(), &reg, &offset);
+
+	if (reg == IRDB_SDK::rn_RIP) 
+	{
+		return getVirtualOffset().getOffset() + getInstructionSize() + offset;
+	}
+	else
+		return 0;
+}
+
+
+int MEDS_FPTRShadowAnnotation::parseRegisterOffset(const char *p_buf)
+{
+	// e.g.: [rsp] [esp+12] [esp-12] 
+	for (auto i = 0U; i < strlen(p_buf); ++i)
+	{
+		if (p_buf[i] == '-' || p_buf[i] == '+')
+		{
+			return atoi(&p_buf[i]);
+		}
+	}
+	return 0;
+}
+
+// e.g.: [rsp] [esp+12] [esp-12] 
+void MEDS_FPTRShadowAnnotation::parseRegister(const char *p_buf, RegisterName *p_register, int *p_registerOffset)
+{
+	int startReg = -1;
+	int endReg = -1;
+	int signPos = -1;
+	for (auto i = 0U; i < strlen(p_buf); ++i)
+	{
+		if (p_buf[i] == '[') startReg = i+1;
+		if (p_buf[i] == ']') 
+		{ 
+			endReg = i-1; 
+		}
+		if (p_buf[i] == '-' || p_buf[i] == '+')
+		{
+			*p_registerOffset = atoi(&p_buf[i]);
+			signPos = i;
+		}
+	}
+
+	if (signPos >= 0)
+		endReg = signPos - 1;
+	if (startReg >= 0 && endReg >= startReg)
+	{
+		char registerBuf[1024];
+		int size = endReg - startReg + 1;
+		strncpy(registerBuf, &p_buf[startReg], size);
+		registerBuf[size] = '\0';
+		cout << "register buffer detected: " << registerBuf << endl;
+		*p_register = Register::getRegister(registerBuf);
+	}
+
+	*p_registerOffset = parseRegisterOffset(p_buf);
+}
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_FRSafeAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_FRSafeAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0b5ed83af64066b91cb78688e5d586325889bd7c
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_FRSafeAnnotation.cpp
@@ -0,0 +1,85 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+
+#include "MEDS_Register.hpp"
+#include "MEDS_FRSafeAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+
+
+
+MEDS_FRSafeAnnotation::MEDS_FRSafeAnnotation(const string &p_rawLine)
+{
+	init();
+	m_rawInputLine=p_rawLine;
+	parse();
+}
+
+void MEDS_FRSafeAnnotation::init()
+{
+}
+
+
+/*
+	Example format (as of July 31, 2014 ) -- subject to change:
+
+   804b3a6      5 INSTR CALL NOFASTRETURN RAUNSAFE ZZ call frame_dummy 
+   804c941      5 INSTR CALL FASTRETURN ZZ call    _ZN7GString3cmpEPKc; GString::cmp(char const*) 
+   804c511      3 INSTR INDIRCALL NOFASTRETURN INDIRECT ZZ call    dword ptr [eax+8] 
+   804c6fa      1 INSTR RETURN NOFASTRETURN NOCALLERS ZZ retn 
+
+*/
+void MEDS_FRSafeAnnotation::parse()
+{
+
+	if (m_rawInputLine.find(" INSTR ")==string::npos)
+                return;
+
+        if (
+		m_rawInputLine.find(" INSTR CALL FASTRETURN ")==string::npos &&
+		m_rawInputLine.find(" INSTR INDCALL FASTRETURN ")==string::npos &&
+		m_rawInputLine.find(" INSTR RETURN FASTRETURN ")==string::npos 
+	   )
+	{
+		/* INSTR  that's not for a safe fast return */
+		return;
+	}
+
+        // get offset
+        VirtualOffset vo(m_rawInputLine);
+        m_virtualOffset = vo;
+
+	setValid();	// no additional info recorded for right now.
+
+//	if(getenv("VERBOSE")!=NULL)
+		cout<<"Found FASTRETURN annotation for "<<vo.to_string()<<endl;
+
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_FuncPrototypeAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_FuncPrototypeAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..8c0ae2c41b1a093f4d8c826669c38ae491d9d755
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_FuncPrototypeAnnotation.cpp
@@ -0,0 +1,126 @@
+/*
+ * Copyright (c) 2014, 2015 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+
+#include "MEDS_Register.hpp"
+#include "MEDS_FuncPrototypeAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+MEDS_FuncPrototypeAnnotation::MEDS_FuncPrototypeAnnotation(const string &p_rawLine)
+{
+	init();
+	m_rawInputLine=p_rawLine;
+	parse();
+}
+
+void MEDS_FuncPrototypeAnnotation::init()
+{
+	MEDS_AnnotationBase::init();
+	m_returnArg = NULL; 
+	m_arguments = NULL;
+}
+
+
+/*
+4046e0     71 FUNC INARGS    4  ARG0 1 ARG1 0 ARG2 0 ARG3 0
+404740    697 FUNC RETURNTYPE RAX 1
+*/
+void MEDS_FuncPrototypeAnnotation::parse()
+{
+	bool about_inargs = false;
+	bool about_return = false;
+
+	if (m_rawInputLine.find("FUNC ")==string::npos)
+		return;
+
+	if (m_rawInputLine.find("INARGS")!=string::npos)
+	{
+		about_inargs = true;
+	}
+
+	if (m_rawInputLine.find("RETURNTYPE")!=string::npos)
+	{
+		about_return = true;
+	}
+
+	if (!about_inargs && !about_return)
+		return;
+
+	// get offset
+	VirtualOffset vo(m_rawInputLine);
+	m_virtualOffset = vo;
+
+	const int maxbufsize = m_rawInputLine.size()*2;
+
+	if (about_inargs)
+	{
+// 4046e0     71 FUNC INARGS    4  ARG0 1 ARG1 0 ARG2 0 ARG3 0
+		int numargs = 0;
+		char buf[maxbufsize]; bzero(buf, maxbufsize);
+		strncpy(buf, m_rawInputLine.c_str(), maxbufsize-1);
+		buf[maxbufsize-1] = '\0';
+		sscanf(buf, "%*x %*d %*s %*s %d %*s", &numargs);
+		for (int i = 0; i < numargs; ++i)
+		{
+			char arg[24];
+			sprintf(arg, "ARG%d", i);			
+			char *zarg = strstr(buf, arg);
+			if (zarg)
+			{
+				int meds_type;
+				sscanf(zarg,"%*s %d", &meds_type);
+				MEDS_Arg marg(meds_type);
+				addArg(marg);
+			}
+			else
+			{
+				setInvalid();
+				return;
+			}
+		}
+	}
+	else if (about_return)
+	{
+		// 404740    697 FUNC RETURNTYPE RAX 1
+		char regbuf[maxbufsize]; bzero(regbuf, maxbufsize);
+		int meds_retType;
+		sscanf(m_rawInputLine.c_str(), "%*x %*d %*s %*s %s %d", regbuf, &meds_retType);
+		RegisterName reg = Register::getRegister(regbuf);
+		MEDS_Arg marg(meds_retType, reg);
+		setReturnArg(marg);
+//		cout << "   adding return argument: " << Register::toString(reg) << " type: " << meds_retType << endl;
+	}
+	else
+	{
+		assert(0);
+		return;
+	}			
+
+	setValid();
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_InstructionCheckAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_InstructionCheckAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..719ebb5f70f1508c8234783e52f26e2c8b0f1ceb
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_InstructionCheckAnnotation.cpp
@@ -0,0 +1,244 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <stdlib.h>
+#include <string.h>
+
+#include "MEDS_Register.hpp"
+#include "MEDS_InstructionCheckAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+/*
+Example format (as of 10/18/2011) -- subject to change:
+
+80482bc 3 INSTR CHECK OVERFLOW UNSIGNED 32 EAX ZZ add eax, 1 
+8048325 6 INSTR CHECK OVERFLOW SIGNED 16 [esp+2AH] ZZ add word ptr [esp+2Ah], 1 
+804832b 6 INSTR CHECK OVERFLOW UNSIGNED 16 [esp+2CH] ZZ add word ptr [esp+2Ch], 1 
+8048336 5 INSTR CHECK SIGNEDNESS SIGNED 16 AX ZZ mov [esp+28h], ax 
+80483db 5 INSTR CHECK UNDERFLOW SIGNED 32 EAX ZZ sub eax, 7FFFFFFFh 
+80483fd 3 INSTR CHECK UNDERFLOW SIGNED 32 EAX ZZ sub eax, 1 
+8048492 5 INSTR CHECK TRUNCATION 32 EAX 16 AX ZZ mov [esp+26h], ax 
+8048492 5 INSTR CHECK SIGNEDNESS SIGNED 16 AX ZZ mov [esp+26h], ax 
+8048892 4 INSTR INFINITELOOP add     [ebp+var_25], 1
+8048293 3 INSTR MEMSET STACKOFFSET 12 SIZE 24 ZZ call memset
+*/
+
+void MEDS_InstructionCheckAnnotation::init()
+{
+	m_isValid = false;
+	m_isOverflow = false;
+	m_isUnderflow = false;
+	m_isTruncation = false;
+	m_isSignedness = false;
+	m_isSigned = false;
+	m_isUnsigned = false;
+	m_isUnknownSign = true;
+	m_isNoFlag = false;
+	m_isInfiniteLoop = false;
+	m_isSevere = false;
+	m_isMemset = false;
+	m_flowsIntoCriticalSink = false;
+	m_isIdiom = false;
+	m_bitWidth = -1;
+	m_truncationFromWidth = -1;
+	m_truncationToWidth = -1;
+	m_register = IRDB_SDK::rn_UNKNOWN;
+	m_register2 = IRDB_SDK::rn_UNKNOWN;
+	m_stackOffset = -1;
+	m_objectSize = -1;
+	m_isEspOffset = false;
+	m_isEbpOffset = false;
+	m_idiomNumber = -1;
+}
+
+MEDS_InstructionCheckAnnotation::MEDS_InstructionCheckAnnotation(const std::string &p_rawInputLine)
+{
+	init();
+	m_rawInputLine = p_rawInputLine;
+	parse();
+}
+
+MEDS_InstructionCheckAnnotation::MEDS_InstructionCheckAnnotation()
+{
+	init();
+}
+
+// parse and set all the member variables
+void MEDS_InstructionCheckAnnotation::parse()
+{
+
+	// format:
+	//	field 1 - instruction address
+	//  field 2 - instruction size (ignore)
+	//  field 3 - INSTR
+	//  field 4 - CHECK | INFINITELOOP | MEMSET
+	//  field 5 - {OVERFLOW | UNDERFLOW | SIGNEDNESS | TRUNCATION }  
+	//  field 6 - {SIGNED | UNSIGNED | UNKNOWNSIGN | 16 | 32}
+	//  field 7 - {<register> | <memory reference>}
+
+	if (m_rawInputLine.find(MEDS_ANNOT_INSTR)==string::npos)
+		return;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_INFINITELOOP)==string::npos &&
+	    m_rawInputLine.find(MEDS_ANNOT_CHECK)==string::npos &&
+	    m_rawInputLine.find(MEDS_ANNOT_MEMSET)==string::npos) 
+	{
+		return;
+	}
+
+	// get offset
+	VirtualOffset vo(m_rawInputLine);
+	m_virtualOffset = vo;
+
+	// The annotation format is very simple so we don't bother with any fancy parsing
+	//   8048913      3 INSTR CHECK OVERFLOW NOFLAGSIGNED 32 EDX+ECX ZZ lea     eax, [edx+ecx]
+	// Later, this may need to be changed
+
+	// get check type
+	if (m_rawInputLine.find(MEDS_ANNOT_OVERFLOW)!=string::npos)
+		m_isOverflow = true;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_UNDERFLOW)!=string::npos)
+		m_isUnderflow = true;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_SIGNEDNESS)!=string::npos)
+		m_isSignedness = true;
+		
+	if (m_rawInputLine.find(MEDS_ANNOT_TRUNCATION)!=string::npos)
+		m_isTruncation = true;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_NOFLAG)!=string::npos)
+		m_isNoFlag = true;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_MEMSET)!=string::npos)
+		m_isMemset = true;
+
+	if (m_rawInputLine.find(MEDS_ANNOT_FLOWS_INTO_CRITICAL_SINK)!=string::npos)
+		m_flowsIntoCriticalSink = true;
+
+	auto idiom_pos = m_rawInputLine.find(MEDS_ANNOT_IDIOM);
+	if (idiom_pos != string::npos)
+	{
+		idiom_pos += strlen(MEDS_ANNOT_IDIOM);
+		setIdiomNumber(atoi(m_rawInputLine.substr(idiom_pos).c_str()));
+		m_isIdiom = true;
+	}
+
+	// signed vs. unsigned
+	if (m_rawInputLine.find(MEDS_ANNOT_UNSIGNED)!=string::npos)
+	{
+		m_isUnsigned = true;
+		m_isUnknownSign = false;
+	}
+	else if (m_rawInputLine.find(MEDS_ANNOT_SIGNED)!=string::npos)
+	{
+		m_isSigned = true;
+		m_isUnknownSign = false;
+	}
+	else if (m_rawInputLine.find(MEDS_ANNOT_UNKNOWNSIGN)!=string::npos)
+	{
+		m_isUnsigned = false;
+		m_isSigned = false;
+		m_isUnknownSign = true;
+	}
+
+    // check for infinite loop annotation
+	// 8048565      3 INSTR INFINITELOOP
+	if (m_rawInputLine.find(MEDS_ANNOT_INFINITELOOP)!=string::npos)
+	{
+		m_isInfiniteLoop = true;
+	}
+
+	const int maxbufsize = m_rawInputLine.size()*2;
+
+	// get bit width information for overflow & underflow
+	if (m_isOverflow || m_isUnderflow)
+	{
+	// 8048565      6 INSTR CHECK OVERFLOW SIGNED 16  [ESP]+38 ZZ add     word ptr [esp+26h], 1
+	// 804856b      6 INSTR CHECK OVERFLOW UNSIGNED 16  [ESP]+36 ZZ add     word ptr [esp+24h], 1
+	// 80483bb      4 INSTR CHECK OVERFLOW UNKNOWNSIGN 16  AX ZZ add     ax, 7FBCh
+	// 80483d5      3 INSTR CHECK UNDERFLOW SIGNED 16  CX ZZ sub     cx, ax
+    // 804d51d      2 INSTR CHECK OVERFLOW UNSIGNED 32  EBX ZZ add     ebx, eax
+
+		char buf[maxbufsize]; bzero(buf, maxbufsize);
+		
+		sscanf(m_rawInputLine.c_str(), "%*s %*d %*s %*s %*s %*s %d %s", &m_bitWidth, buf);
+		m_target = string(buf);
+		if (m_isNoFlag)
+		{
+			m_register = Register::getRegister(m_target);
+		}
+	}
+	else if (m_isTruncation) // get bid width from/to information for truncation
+	{
+		char buf[maxbufsize]; bzero(buf, maxbufsize);
+		char buf2[maxbufsize]; bzero(buf2, maxbufsize);
+		// [ADDR] [SIZE] INSTR CHECK TRUNCATION UNKNOWNSIGN 32 EAX 16 AX ZZ mov     [esp+2Ah], ax
+		sscanf(m_rawInputLine.c_str(), "%*s %*d %*s %*s %*s %*s %d %s %d %s", &m_truncationFromWidth, buf, &m_truncationToWidth, buf2);
+
+		m_target = string(buf);
+		m_target2 = string(buf2);
+
+		m_register = Register::getRegister(m_target);
+		m_register2 = Register::getRegister(m_target2);
+
+		// 20120410 STARS added SEVERE field to TRUNC annotations to specify that we must use a terminating/saturating policy
+		if (m_rawInputLine.find(MEDS_ANNOT_SEVERE)!=string::npos)
+		{
+			m_isSevere = true;
+		}
+	} 
+	else if (m_isSignedness)
+	{
+		char buf[maxbufsize]; bzero(buf, maxbufsize);
+		// [ADDR] [SIZE] INSTR CHECK SIGNEDNESS SIGNED 16 AX ZZ mov     [esp+28h], ax
+		// [ADDR] [SIZE] INSTR CHECK SIGNEDNESS UNSIGNED 16 AX ZZ mov   [esp+28h], ax
+		sscanf(m_rawInputLine.c_str(), "%*s %*d %*s %*s %*s %*s %d %s", &m_bitWidth, buf);
+		m_target = string(buf);
+		m_register = Register::getRegister(m_target);
+	}
+
+	if (m_isMemset)
+	{
+		// 8048293 3 INSTR MEMSET STACKOFFSET_EBP 12 SIZE 24 ZZ call memset
+		// 8048293 3 INSTR MEMSET STACKOFFSET_ESP 12 SIZE 24 ZZ call memset
+		if (m_rawInputLine.find("STACKOFFSET")!=string::npos)
+		{
+			char buf[maxbufsize]; bzero(buf, maxbufsize);
+			sscanf(m_rawInputLine.c_str(), "%*s %*d %*s %*s %*s %d %*s %d", &m_stackOffset, &m_objectSize);
+			if (m_rawInputLine.find("STACKOFFSET_EBP")!=string::npos)
+			{
+				m_isEbpOffset = true;
+			}
+			else if (m_rawInputLine.find("STACKOFFSET_ESP")!=string::npos)
+			{
+				m_isEspOffset = true;
+			}
+		}
+	}
+
+	setValid(); // m_isValid = true;
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_MemoryRangeAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_MemoryRangeAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d3475148d00396c1de0ed0da0f9512464cb95e7e
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_MemoryRangeAnnotation.cpp
@@ -0,0 +1,162 @@
+/*
+ * Copyright (c) 2018 - University of Virginia
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.edu
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+#include <cinttypes>
+
+#include "MEDS_MemoryRangeAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+/*
+	Example format -- subject to change:
+
+	417748     12 INSTR STATICMEMWRITE MIN 3c60320  LIMIT 4e53730  ZZ
+	4992ea      4 INSTR STACKMEMRANGE MIN RSP-568 LIMIT RSP-48 INSTRSPDELTA -592 ZZ
+	4992ea      4 INSTR SENTINEL BASE 43d920 OFFSET -8 ZZ
+
+	See explanations in the header file MEDS_MemoryRangeAnnotation.hpp.
+
+*/
+
+MEDS_MemoryRangeAnnotation::MEDS_MemoryRangeAnnotation() : MEDS_AnnotationBase()
+{
+	this->setInvalid();	
+	this->setStackRange(false);
+	this->setStaticGlobalRange(false);
+	this->setSentinel(false);
+}
+
+MEDS_MemoryRangeAnnotation::MEDS_MemoryRangeAnnotation(const string &p_rawLine) : MEDS_AnnotationBase()
+{
+	this->setInvalid();
+	this->setStackRange(false);
+	this->setStaticGlobalRange(false);
+	this->setSentinel(false);
+	this->m_rawInputLine = p_rawLine;
+	this->parse();
+}
+
+void MEDS_MemoryRangeAnnotation::parse()
+{
+	if (this->m_rawInputLine.find(" INSTR ") == string::npos)
+		return;
+
+	if (this->m_rawInputLine.find(MEDS_ANNOT_STATICMEMWRITE) != string::npos)
+	{
+		this->setStaticGlobalRange(true);
+	}
+
+	if (this->m_rawInputLine.find(MEDS_ANNOT_STACKMEMRANGE) != string::npos)
+	{
+		this->setStackRange(true);
+	}
+
+	if (this->m_rawInputLine.find(MEDS_ANNOT_SENTINEL) != string::npos)
+	{
+		this->setSentinel(true);
+	}
+
+	if (!this->isStackRange() && !this->isStaticGlobalRange() && !this->isSentinel())
+	{
+		/* invalid annotation */
+		this->setInvalid();	
+		return;
+	}
+
+	// get offset
+	VirtualOffset vo(m_rawInputLine);
+	this->setVirtualOffset(vo); // in base class
+
+	uint64_t MinVal, LimitVal;
+	int64_t OffsetVal;
+	int instrSize;
+
+	// 417748     12 INSTR STATICMEMWRITE MIN 3c60320  LIMIT 4e53730  ZZ
+	// 4992ea      4 INSTR STACKMEMRANGE MIN RSP - 568 LIMIT RSP - 48 INSTRSPDELTA - 592 ZZ
+	if (this->isStaticGlobalRange()) {
+		int ItemsFilled = sscanf(m_rawInputLine.c_str(), "%*x %d %*s %*s MIN %" SCNx64 " LIMIT %" SCNx64, &instrSize, &MinVal, &LimitVal);
+		if (3 != ItemsFilled) {
+			this->setInvalid();
+			cerr << "Error on sscanf of annotation: ItemsFilled = " << ItemsFilled << " line: " << m_rawInputLine << endl;
+			return;
+		}
+		else {
+			cerr << "Parsed STATICMEMWRITE annotation: MIN = " << hex << MinVal << " LIMIT = " << LimitVal << endl;
+		}
+	}
+	else if (this->isStackRange()) {
+#if 0
+		int ItemsFilled = sscanf(m_rawInputLine.c_str(), "%*x %d %*s %*s MIN %" SCNx64 " LIMIT %" SCNx64, &instrSize, &MinVal, &LimitVal);
+		if (3 != ItemsFilled) {
+			this->setInvalid();
+			cerr << "Error on sscanf of annotation: ItemsFilled = " << ItemsFilled << " line: " << m_rawInputLine << endl;
+			return;
+		}
+#else
+		this->setInvalid();
+		cerr << "Not yet parsing STACKMEMRANGE annotations " << endl;
+		return;
+#endif
+	}
+	else { // SENTINEL
+		int ItemsFilled = sscanf(m_rawInputLine.c_str(), "%*x %d %*s %*s BASE %" SCNx64 " OFFSET %" SCNd64, &instrSize, &MinVal, &OffsetVal);
+		if (3 != ItemsFilled) {
+			this->setInvalid();
+			cerr << "Error on sscanf of annotation: ItemsFilled = " << ItemsFilled << " line: " << m_rawInputLine << endl;
+			return;
+		}
+	}
+
+	this->setInstructionSize(instrSize); // in base class
+	this->setRangeMin(MinVal);
+	if (this->isSentinel()) {
+		this->setSentinelOffset(OffsetVal);
+	}
+	else {
+		this->setRangeLimit(LimitVal);
+	}
+
+	cout << "virtual offset: " << hex << this->getVirtualOffset().getOffset() << dec << endl;
+	cout << "size: " << this->getInstructionSize() << endl;
+	cout << "min: " << this->getRangeMin() << endl;
+	if (this->isSentinel()) {
+		cout << "offset: " << this->getSentinelOffset() << endl;
+	}
+	else {
+		cout << "limit: " << this->getRangeLimit() << endl;
+
+		if (LimitVal <= MinVal)
+		{
+			setInvalid();
+			cerr << "invalid range limit" << endl;
+			return;
+		}
+	}
+
+	cout << "valid annotation" << endl;
+	this->setValid();
+} // end of MEDS_MemoryRangeAnnotation::parse()
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_ProblemFuncAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_ProblemFuncAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b42d0d1af848a2d0488fbf30feadd7d040c788ce
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_ProblemFuncAnnotation.cpp
@@ -0,0 +1,104 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include <iostream>
+#include <cstdio>
+#include <string>
+
+#include "MEDS_Register.hpp"
+#include "MEDS_ProblemFuncAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+
+
+
+MEDS_ProblemFuncAnnotation::MEDS_ProblemFuncAnnotation(const string &p_rawLine)
+{
+	init();
+	m_rawInputLine=p_rawLine;
+	parse();
+}
+
+void MEDS_ProblemFuncAnnotation::init()
+{
+	MEDS_FuncAnnotation::init();
+}
+
+
+/*
+	Example format (as of August 15, 2014 ) -- subject to change:
+
+    400420      6 FUNC PROBLEM .__libc_start_main JUMPUNRESOLVED
+    400430      6 FUNC PROBLEM .__printf_chk CHUNKS JUMPUNRESOLVED
+    400490    100 FUNC PROBLEM __do_global_dtors_aux CALLUNRESOLVED
+
+
+*/
+void MEDS_ProblemFuncAnnotation::parse()
+{
+
+	if (m_rawInputLine.find("FUNC ")==string::npos)
+                return;
+
+        size_t pos=m_rawInputLine.find("FUNC PROBLEM");
+        if ( pos==string::npos )
+	{
+		/* FUNC line that's not local or global?  I'm confused. */
+		/* could be a FUNC GLOBAL, etc. line */
+		return;
+	}
+
+	size_t func_name_start_pos=pos+strlen("FUNC PROBLEM ");
+	size_t func_end_pos=m_rawInputLine.find(" ", func_name_start_pos);
+	assert(func_end_pos!=string::npos);
+	string func_name=m_rawInputLine.substr(func_name_start_pos, func_end_pos-func_name_start_pos);
+
+        // get offset
+	setFuncName(func_name);
+	cout<<"Found problem func name='"<<func_name<<"'"<<endl;
+
+	if(!isValid()) matches(m_rawInputLine,"JUMPUNRSOLVED", pt_JumpUnresolved);
+	if(!isValid()) matches(m_rawInputLine,"CALLUNRSOLVED", pt_CallUnresolved);
+	if(!isValid()) matches(m_rawInputLine,"STACKANALYSIS", pt_BadStackAnalysis);
+	if(!isValid()) matches(m_rawInputLine,"BADRTLS", pt_BadRTLs);
+	if(!isValid()) 
+	{
+		pt=pt_Unknown;
+		setValid();
+	}
+	
+}
+
+void MEDS_ProblemFuncAnnotation::matches(string line, string pattern, ProblemType prob_type)
+{
+	
+        if (line.find(pattern)!=string::npos)
+	{
+		if(getenv("VERBOSE"))
+			cout<<"Found "<<pattern<<" problem annotation for "<<getFuncName() << endl;
+		pt=prob_type;
+		setValid();
+	}
+}
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_Register.cpp b/irdb-lib/libMEDSannotation/src/MEDS_Register.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..36741f094d56be4bb96f549c7fd16a28eeeb4ef3
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_Register.cpp
@@ -0,0 +1,588 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <string>
+#include <sstream>
+#include <strings.h>
+#include <assert.h>
+
+#include "MEDS_Register.hpp"
+
+using namespace MEDS_Annotation;
+using namespace std;
+
+RegisterName Register::getRegister(char *p_reg)
+{
+	return Register::getRegister(std::string(p_reg));
+}
+
+bool Register::isValidRegister(std::string p_reg)
+{
+	return getRegister(p_reg) != IRDB_SDK::rn_UNKNOWN;
+}
+
+bool Register::isValidRegister(const RegisterName p_reg)
+{
+	return isValidRegister(Register::toString(p_reg));
+}
+
+RegisterName Register::getRegister(std::string p_reg)
+{
+	if (strcasecmp(p_reg.c_str(), "EFLAGS") ==0)
+		return IRDB_SDK::rn_EFLAGS;
+	else if (strcasecmp(p_reg.c_str(), "RAX") == 0)
+		return IRDB_SDK::rn_RAX;
+	else if (strcasecmp(p_reg.c_str(), "RBX") == 0)
+		return IRDB_SDK::rn_RBX;
+	else if (strcasecmp(p_reg.c_str(), "RCX") == 0)
+		return IRDB_SDK::rn_RCX;
+	else if (strcasecmp(p_reg.c_str(), "RDX") == 0)
+		return IRDB_SDK::rn_RDX;
+	else if (strcasecmp(p_reg.c_str(), "RSI") == 0)
+		return IRDB_SDK::rn_RSI;
+	else if (strcasecmp(p_reg.c_str(), "RDI") == 0)
+		return IRDB_SDK::rn_RDI;
+	else if (strcasecmp(p_reg.c_str(), "RBP") == 0)
+		return IRDB_SDK::rn_RBP;
+	else if (strcasecmp(p_reg.c_str(), "RSP") == 0)
+		return IRDB_SDK::rn_RSP;
+	else if (strcasecmp(p_reg.c_str(), "R8") == 0)
+		return IRDB_SDK::rn_R8;
+	else if (strcasecmp(p_reg.c_str(), "R9") == 0)
+		return IRDB_SDK::rn_R9;
+	else if (strcasecmp(p_reg.c_str(), "R10") == 0)
+		return IRDB_SDK::rn_R10;
+	else if (strcasecmp(p_reg.c_str(), "R11") == 0)
+		return IRDB_SDK::rn_R11;
+	else if (strcasecmp(p_reg.c_str(), "R12") == 0)
+		return IRDB_SDK::rn_R12;
+	else if (strcasecmp(p_reg.c_str(), "R13") == 0)
+		return IRDB_SDK::rn_R13;
+	else if (strcasecmp(p_reg.c_str(), "R14") == 0)
+		return IRDB_SDK::rn_R14;
+	else if (strcasecmp(p_reg.c_str(), "R15") == 0)
+		return IRDB_SDK::rn_R15;
+	else if (strcasecmp(p_reg.c_str(), "RIP") == 0)
+		return IRDB_SDK::rn_RIP;
+
+	else if (strcasecmp(p_reg.c_str(), "EAX") == 0)
+		return IRDB_SDK::rn_EAX;
+	else if (strcasecmp(p_reg.c_str(), "EBX") == 0)
+		return IRDB_SDK::rn_EBX;
+	else if (strcasecmp(p_reg.c_str(), "ECX") == 0)
+		return IRDB_SDK::rn_ECX;
+	else if (strcasecmp(p_reg.c_str(), "EDX") == 0)
+		return IRDB_SDK::rn_EDX;
+	else if (strcasecmp(p_reg.c_str(), "ESI") == 0)
+		return IRDB_SDK::rn_ESI;
+	else if (strcasecmp(p_reg.c_str(), "EDI") == 0)
+		return IRDB_SDK::rn_EDI;
+	else if (strcasecmp(p_reg.c_str(), "EBP") == 0)
+		return IRDB_SDK::rn_EBP;
+	else if (strcasecmp(p_reg.c_str(), "ESP") == 0)
+		return IRDB_SDK::rn_ESP;
+	else if (strcasecmp(p_reg.c_str(), "R8D") == 0)
+		return IRDB_SDK::rn_R8D;
+	else if (strcasecmp(p_reg.c_str(), "R9D") == 0)
+		return IRDB_SDK::rn_R9D;
+	else if (strcasecmp(p_reg.c_str(), "R10D") == 0)
+		return IRDB_SDK::rn_R10D;
+	else if (strcasecmp(p_reg.c_str(), "R11D") == 0)
+		return IRDB_SDK::rn_R11D;
+	else if (strcasecmp(p_reg.c_str(), "R12D") == 0)
+		return IRDB_SDK::rn_R12D;
+	else if (strcasecmp(p_reg.c_str(), "R13D") == 0)
+		return IRDB_SDK::rn_R13D;
+	else if (strcasecmp(p_reg.c_str(), "R14D") == 0)
+		return IRDB_SDK::rn_R14D;
+	else if (strcasecmp(p_reg.c_str(), "R15D") == 0)
+		return IRDB_SDK::rn_R15D;
+
+	else if (strcasecmp(p_reg.c_str(), "AX") == 0)
+		return IRDB_SDK::rn_AX;
+	else if (strcasecmp(p_reg.c_str(), "BX") == 0)
+		return IRDB_SDK::rn_BX;
+	else if (strcasecmp(p_reg.c_str(), "CX") == 0)
+		return IRDB_SDK::rn_CX;
+	else if (strcasecmp(p_reg.c_str(), "DX") == 0)
+		return IRDB_SDK::rn_DX;
+	else if (strcasecmp(p_reg.c_str(), "BP") == 0)
+		return IRDB_SDK::rn_BP;
+	else if (strcasecmp(p_reg.c_str(), "SP") == 0)
+		return IRDB_SDK::rn_SP;
+	else if (strcasecmp(p_reg.c_str(), "SI") == 0)
+		return IRDB_SDK::rn_SI;
+	else if (strcasecmp(p_reg.c_str(), "DI") == 0)
+		return IRDB_SDK::rn_DI;
+	else if (strcasecmp(p_reg.c_str(), "R8W") == 0)
+		return IRDB_SDK::rn_R8W;
+	else if (strcasecmp(p_reg.c_str(), "R9W") == 0)
+		return IRDB_SDK::rn_R9W;
+	else if (strcasecmp(p_reg.c_str(), "R10W") == 0)
+		return IRDB_SDK::rn_R10W;
+	else if (strcasecmp(p_reg.c_str(), "R11W") == 0)
+		return IRDB_SDK::rn_R11W;
+	else if (strcasecmp(p_reg.c_str(), "R12W") == 0)
+		return IRDB_SDK::rn_R12W;
+	else if (strcasecmp(p_reg.c_str(), "R13W") == 0)
+		return IRDB_SDK::rn_R13W;
+	else if (strcasecmp(p_reg.c_str(), "R14W") == 0)
+		return IRDB_SDK::rn_R14W;
+	else if (strcasecmp(p_reg.c_str(), "R15W") == 0)
+		return IRDB_SDK::rn_R15W;
+
+	else if (strcasecmp(p_reg.c_str(), "AH") == 0)
+		return IRDB_SDK::rn_AL;
+	else if (strcasecmp(p_reg.c_str(), "BH") == 0)
+		return IRDB_SDK::rn_BL;
+	else if (strcasecmp(p_reg.c_str(), "CH") == 0)
+		return IRDB_SDK::rn_CL;
+	else if (strcasecmp(p_reg.c_str(), "DH") == 0)
+		return IRDB_SDK::rn_DL;
+	else if (strcasecmp(p_reg.c_str(), "AL") == 0)
+		return IRDB_SDK::rn_AL;
+	else if (strcasecmp(p_reg.c_str(), "BL") == 0)
+		return IRDB_SDK::rn_BL;
+	else if (strcasecmp(p_reg.c_str(), "CL") == 0)
+		return IRDB_SDK::rn_CL;
+	else if (strcasecmp(p_reg.c_str(), "DL") == 0)
+		return IRDB_SDK::rn_DL;
+	else if (strcasecmp(p_reg.c_str(), "SIL") == 0)
+		return IRDB_SDK::rn_SIL;
+	else if (strcasecmp(p_reg.c_str(), "DIL") == 0)
+		return IRDB_SDK::rn_DIL;
+	else if (strcasecmp(p_reg.c_str(), "BPL") == 0)
+		return IRDB_SDK::rn_BPL;
+	else if (strcasecmp(p_reg.c_str(), "SPL") == 0)
+		return IRDB_SDK::rn_SPL;
+	else if (strcasecmp(p_reg.c_str(), "R8B") == 0)
+		return IRDB_SDK::rn_R8B;
+	else if (strcasecmp(p_reg.c_str(), "R9B") == 0)
+		return IRDB_SDK::rn_R9B;
+	else if (strcasecmp(p_reg.c_str(), "R10B") == 0)
+		return IRDB_SDK::rn_R10B;
+	else if (strcasecmp(p_reg.c_str(), "R11B") == 0)
+		return IRDB_SDK::rn_R11B;
+	else if (strcasecmp(p_reg.c_str(), "R12B") == 0)
+		return IRDB_SDK::rn_R12B;
+	else if (strcasecmp(p_reg.c_str(), "R13B") == 0)
+		return IRDB_SDK::rn_R13B;
+	else if (strcasecmp(p_reg.c_str(), "R14B") == 0)
+		return IRDB_SDK::rn_R14B;
+	else if (strcasecmp(p_reg.c_str(), "R15B") == 0)
+		return IRDB_SDK::rn_R15B;
+	else
+		return IRDB_SDK::rn_UNKNOWN;
+}
+
+bool Register::is8bit(RegisterName p_reg)
+{
+	return p_reg == IRDB_SDK::rn_AL || p_reg == IRDB_SDK::rn_BL || p_reg == IRDB_SDK::rn_CL || p_reg == IRDB_SDK::rn_DL ||
+		p_reg == IRDB_SDK::rn_AH || p_reg == IRDB_SDK::rn_BH || p_reg == IRDB_SDK::rn_CH || p_reg == IRDB_SDK::rn_DH ||
+		p_reg == IRDB_SDK::rn_SIL || p_reg == IRDB_SDK::rn_DIL || p_reg == IRDB_SDK::rn_BPL || p_reg == IRDB_SDK::rn_SPL ||
+		p_reg == IRDB_SDK::rn_R8B || p_reg == IRDB_SDK::rn_R9B || p_reg == IRDB_SDK::rn_R10B || p_reg == IRDB_SDK::rn_R11B ||
+		p_reg == IRDB_SDK::rn_R12B || p_reg == IRDB_SDK::rn_R13B || p_reg == IRDB_SDK::rn_R14B || p_reg == IRDB_SDK::rn_R15B;
+}
+
+bool Register::is16bit(RegisterName p_reg)
+{
+	return p_reg == IRDB_SDK::rn_AX || p_reg == IRDB_SDK::rn_BX || p_reg == IRDB_SDK::rn_CX || p_reg == IRDB_SDK::rn_DX ||
+		p_reg == IRDB_SDK::rn_BP || p_reg == IRDB_SDK::rn_SP || p_reg == IRDB_SDK::rn_SI || p_reg == IRDB_SDK::rn_DI ||
+		p_reg == IRDB_SDK::rn_R8W || p_reg == IRDB_SDK::rn_R9W || p_reg == IRDB_SDK::rn_R10W || p_reg == IRDB_SDK::rn_R11W ||
+		p_reg == IRDB_SDK::rn_R12W || p_reg == IRDB_SDK::rn_R13W || p_reg == IRDB_SDK::rn_R14W || p_reg == IRDB_SDK::rn_R15W;
+}
+
+bool Register::is32bit(RegisterName p_reg)
+{
+	return p_reg == IRDB_SDK::rn_EAX || p_reg == IRDB_SDK::rn_EBX || p_reg == IRDB_SDK::rn_ECX || p_reg == IRDB_SDK::rn_EDX || 
+		p_reg == IRDB_SDK::rn_ESI || p_reg == IRDB_SDK::rn_EDI || p_reg == IRDB_SDK::rn_ESP || p_reg == IRDB_SDK::rn_EBP ||
+		p_reg == IRDB_SDK::rn_R8D || p_reg == IRDB_SDK::rn_R9D || p_reg == IRDB_SDK::rn_R10D || p_reg == IRDB_SDK::rn_R11D ||
+		p_reg == IRDB_SDK::rn_R12D || p_reg == IRDB_SDK::rn_R13D || p_reg == IRDB_SDK::rn_R14D || p_reg == IRDB_SDK::rn_R15D;
+}
+
+bool Register::is64bit(RegisterName p_reg)
+{
+	return p_reg == IRDB_SDK::rn_RAX || p_reg == IRDB_SDK::rn_RBX || p_reg == IRDB_SDK::rn_RCX || p_reg == IRDB_SDK::rn_RDX || 
+		p_reg == IRDB_SDK::rn_RSI || p_reg == IRDB_SDK::rn_RDI || p_reg == IRDB_SDK::rn_RBP || p_reg == IRDB_SDK::rn_RSP ||
+		p_reg == IRDB_SDK::rn_R8 || p_reg == IRDB_SDK::rn_R9 || p_reg == IRDB_SDK::rn_R10 || p_reg == IRDB_SDK::rn_R11 || 
+		p_reg == IRDB_SDK::rn_R12 || p_reg == IRDB_SDK::rn_R13 || p_reg == IRDB_SDK::rn_R14 || p_reg == IRDB_SDK::rn_R15 || p_reg == IRDB_SDK::rn_RIP;
+}
+
+std::string Register::toString(RegisterName p_reg)
+{
+	if (p_reg == IRDB_SDK::rn_UNKNOWN) return std::string("UNKNOWN");
+
+	else if (p_reg == IRDB_SDK::rn_EFLAGS) return std::string("EFLAGS");
+
+	else if (p_reg == IRDB_SDK::rn_RAX) return std::string("RAX");
+	else if (p_reg == IRDB_SDK::rn_RBX) return std::string("RBX");
+	else if (p_reg == IRDB_SDK::rn_RCX) return std::string("RCX");
+	else if (p_reg == IRDB_SDK::rn_RDX) return std::string("RDX");
+	else if (p_reg == IRDB_SDK::rn_RSI) return std::string("RSI");
+	else if (p_reg == IRDB_SDK::rn_RDI) return std::string("RDI");
+	else if (p_reg == IRDB_SDK::rn_RBP) return std::string("RBP");
+	else if (p_reg == IRDB_SDK::rn_RSP) return std::string("RSP");
+	else if (p_reg == IRDB_SDK::rn_R8) return std::string("R8");
+	else if (p_reg == IRDB_SDK::rn_R9) return std::string("R9");
+	else if (p_reg == IRDB_SDK::rn_R10) return std::string("R10");
+	else if (p_reg == IRDB_SDK::rn_R11) return std::string("R11");
+	else if (p_reg == IRDB_SDK::rn_R12) return std::string("R12");
+	else if (p_reg == IRDB_SDK::rn_R13) return std::string("R13");
+	else if (p_reg == IRDB_SDK::rn_R14) return std::string("R14");
+	else if (p_reg == IRDB_SDK::rn_R15) return std::string("R15");
+	else if (p_reg == IRDB_SDK::rn_RIP) return std::string("RIP");
+
+	else if (p_reg == IRDB_SDK::rn_EAX) return std::string("EAX");
+	else if (p_reg == IRDB_SDK::rn_EBX) return std::string("EBX");
+	else if (p_reg == IRDB_SDK::rn_ECX) return std::string("ECX");
+	else if (p_reg == IRDB_SDK::rn_EDX) return std::string("EDX");
+	else if (p_reg == IRDB_SDK::rn_EDI) return std::string("EDI");
+	else if (p_reg == IRDB_SDK::rn_ESI) return std::string("ESI");
+	else if (p_reg == IRDB_SDK::rn_EBP) return std::string("EBP");
+	else if (p_reg == IRDB_SDK::rn_ESP) return std::string("ESP");
+	else if (p_reg == IRDB_SDK::rn_R8D) return std::string("R8D");
+	else if (p_reg == IRDB_SDK::rn_R9D) return std::string("R9D");
+	else if (p_reg == IRDB_SDK::rn_R10D) return std::string("R10D");
+	else if (p_reg == IRDB_SDK::rn_R11D) return std::string("R11D");
+	else if (p_reg == IRDB_SDK::rn_R12D) return std::string("R12D");
+	else if (p_reg == IRDB_SDK::rn_R13D) return std::string("R13D");
+	else if (p_reg == IRDB_SDK::rn_R14D) return std::string("R14D");
+	else if (p_reg == IRDB_SDK::rn_R15D) return std::string("R15D");
+
+	else if (p_reg == IRDB_SDK::rn_AX) return std::string("AX");
+	else if (p_reg == IRDB_SDK::rn_BX) return std::string("BX");
+	else if (p_reg == IRDB_SDK::rn_CX) return std::string("CX");
+	else if (p_reg == IRDB_SDK::rn_DX) return std::string("DX");
+	else if (p_reg == IRDB_SDK::rn_BP) return std::string("BP");
+	else if (p_reg == IRDB_SDK::rn_SP) return std::string("SP");
+	else if (p_reg == IRDB_SDK::rn_SI) return std::string("SI");
+	else if (p_reg == IRDB_SDK::rn_DI) return std::string("DI");
+	else if (p_reg == IRDB_SDK::rn_R8W) return std::string("R8W");
+	else if (p_reg == IRDB_SDK::rn_R9W) return std::string("R9W");
+	else if (p_reg == IRDB_SDK::rn_R10W) return std::string("R10W");
+	else if (p_reg == IRDB_SDK::rn_R11W) return std::string("R11W");
+	else if (p_reg == IRDB_SDK::rn_R12W) return std::string("R12W");
+	else if (p_reg == IRDB_SDK::rn_R13W) return std::string("R13W");
+	else if (p_reg == IRDB_SDK::rn_R14W) return std::string("R14W");
+	else if (p_reg == IRDB_SDK::rn_R15W) return std::string("R15W");
+
+	else if (p_reg == IRDB_SDK::rn_AH) return std::string("AH");
+	else if (p_reg == IRDB_SDK::rn_BH) return std::string("BH");
+	else if (p_reg == IRDB_SDK::rn_CH) return std::string("CH");
+	else if (p_reg == IRDB_SDK::rn_DH) return std::string("DH");
+	else if (p_reg == IRDB_SDK::rn_AL) return std::string("AL");
+	else if (p_reg == IRDB_SDK::rn_BL) return std::string("BL");
+	else if (p_reg == IRDB_SDK::rn_CL) return std::string("CL");
+	else if (p_reg == IRDB_SDK::rn_DL) return std::string("DL");
+	else if (p_reg == IRDB_SDK::rn_SIL) return std::string("SIL");
+	else if (p_reg == IRDB_SDK::rn_DIL) return std::string("DIL");
+	else if (p_reg == IRDB_SDK::rn_BPL) return std::string("BPL");
+	else if (p_reg == IRDB_SDK::rn_SPL) return std::string("SPL");
+	else if (p_reg == IRDB_SDK::rn_R8B) return std::string("R8B");
+	else if (p_reg == IRDB_SDK::rn_R9B) return std::string("R9B");
+	else if (p_reg == IRDB_SDK::rn_R10B) return std::string("R10B");
+	else if (p_reg == IRDB_SDK::rn_R11B) return std::string("R11B");
+	else if (p_reg == IRDB_SDK::rn_R12B) return std::string("R12B");
+	else if (p_reg == IRDB_SDK::rn_R13B) return std::string("R13B");
+	else if (p_reg == IRDB_SDK::rn_R14B) return std::string("R14B");
+	else if (p_reg == IRDB_SDK::rn_R15B) return std::string("R15B");
+
+	else return std::string("UNEXPECTED REGISTER VALUE");
+}
+
+int Register::getBitWidth(RegisterName p_reg)
+{
+	switch (p_reg)
+	{
+		case IRDB_SDK::rn_RAX:
+		case IRDB_SDK::rn_RBX:
+		case IRDB_SDK::rn_RCX:
+		case IRDB_SDK::rn_RDX:
+		case IRDB_SDK::rn_RSI:
+		case IRDB_SDK::rn_RDI:
+		case IRDB_SDK::rn_RBP:
+		case IRDB_SDK::rn_RSP:
+		case IRDB_SDK::rn_R8:
+		case IRDB_SDK::rn_R9:
+		case IRDB_SDK::rn_R10:
+		case IRDB_SDK::rn_R11:
+		case IRDB_SDK::rn_R12:
+		case IRDB_SDK::rn_R13:
+		case IRDB_SDK::rn_R14:
+		case IRDB_SDK::rn_R15:
+		case IRDB_SDK::rn_RIP:
+			return 64;
+			break;
+		case IRDB_SDK::rn_EAX:
+		case IRDB_SDK::rn_EBX:
+		case IRDB_SDK::rn_ECX:
+		case IRDB_SDK::rn_EDX:
+		case IRDB_SDK::rn_EDI:
+		case IRDB_SDK::rn_ESI:
+		case IRDB_SDK::rn_EBP:
+		case IRDB_SDK::rn_ESP:
+		case IRDB_SDK::rn_R8D:
+		case IRDB_SDK::rn_R9D:
+		case IRDB_SDK::rn_R10D:
+		case IRDB_SDK::rn_R11D:
+		case IRDB_SDK::rn_R12D:
+		case IRDB_SDK::rn_R13D:
+		case IRDB_SDK::rn_R14D:
+		case IRDB_SDK::rn_R15D:
+			return 32;
+			break;
+
+		case IRDB_SDK::rn_AX:				
+		case IRDB_SDK::rn_BX:				
+		case IRDB_SDK::rn_CX:				
+		case IRDB_SDK::rn_DX:				
+		case IRDB_SDK::rn_BP:				
+		case IRDB_SDK::rn_SP:				
+		case IRDB_SDK::rn_SI:				
+		case IRDB_SDK::rn_DI:				
+		case IRDB_SDK::rn_R8W:
+		case IRDB_SDK::rn_R9W:
+		case IRDB_SDK::rn_R10W:
+		case IRDB_SDK::rn_R11W:
+		case IRDB_SDK::rn_R12W:
+		case IRDB_SDK::rn_R13W:
+		case IRDB_SDK::rn_R14W:
+		case IRDB_SDK::rn_R15W:
+			return 16;
+			break;
+
+		case IRDB_SDK::rn_AH:				
+		case IRDB_SDK::rn_BH:				
+		case IRDB_SDK::rn_CH:				
+		case IRDB_SDK::rn_DH:				
+		case IRDB_SDK::rn_AL:				
+		case IRDB_SDK::rn_BL:				
+		case IRDB_SDK::rn_CL:				
+		case IRDB_SDK::rn_DL:				
+		case IRDB_SDK::rn_SIL:
+		case IRDB_SDK::rn_DIL:
+		case IRDB_SDK::rn_BPL:
+		case IRDB_SDK::rn_SPL:
+		case IRDB_SDK::rn_R8B:
+		case IRDB_SDK::rn_R9B:
+		case IRDB_SDK::rn_R10B:
+		case IRDB_SDK::rn_R11B:
+		case IRDB_SDK::rn_R12B:
+		case IRDB_SDK::rn_R13B:
+		case IRDB_SDK::rn_R14B:
+		case IRDB_SDK::rn_R15B:
+			return 8;
+			break;
+
+		default:
+			return -1;
+			break;
+	}
+}
+
+
+// favor registers R10..R15
+RegisterName Register::getFreeRegister64(const RegisterSet_t& p_taken)
+{
+
+#define ret_if_free4(a, b, c, d)\
+	if (p_taken.count(a) == 0 && p_taken.count(b) == 0 && p_taken.count(c) == 0 && p_taken.count(d) == 0 ) \
+		return a; \
+
+#define ret_if_free5(a, b, c, d, e)\
+	if (p_taken.count(a) == 0 && p_taken.count(b) == 0 && p_taken.count(c) == 0 && p_taken.count(d) == 0  && p_taken.count(e)==0) \
+		return a; \
+
+	ret_if_free4(IRDB_SDK::rn_R8, IRDB_SDK::rn_R8D, IRDB_SDK::rn_R8W, IRDB_SDK::rn_R8B);
+	ret_if_free4(IRDB_SDK::rn_R9, IRDB_SDK::rn_R9D, IRDB_SDK::rn_R9W, IRDB_SDK::rn_R9B);
+	ret_if_free4(IRDB_SDK::rn_R10, IRDB_SDK::rn_R10D, IRDB_SDK::rn_R10W, IRDB_SDK::rn_R10B);
+	ret_if_free4(IRDB_SDK::rn_R11, IRDB_SDK::rn_R11D, IRDB_SDK::rn_R11W, IRDB_SDK::rn_R11B);
+	ret_if_free4(IRDB_SDK::rn_R12, IRDB_SDK::rn_R12D, IRDB_SDK::rn_R12W, IRDB_SDK::rn_R12B);
+	ret_if_free4(IRDB_SDK::rn_R13, IRDB_SDK::rn_R13D, IRDB_SDK::rn_R13W, IRDB_SDK::rn_R13B);
+	ret_if_free4(IRDB_SDK::rn_R14, IRDB_SDK::rn_R14D, IRDB_SDK::rn_R14W, IRDB_SDK::rn_R14B);
+	ret_if_free4(IRDB_SDK::rn_R15, IRDB_SDK::rn_R15D, IRDB_SDK::rn_R15W, IRDB_SDK::rn_R15B);
+	ret_if_free5(IRDB_SDK::rn_RAX, IRDB_SDK::rn_EAX, IRDB_SDK::rn_AX, IRDB_SDK::rn_AL, IRDB_SDK::rn_AH);
+	ret_if_free5(IRDB_SDK::rn_RCX, IRDB_SDK::rn_ECX, IRDB_SDK::rn_CX, IRDB_SDK::rn_CL, IRDB_SDK::rn_CH);
+	ret_if_free5(IRDB_SDK::rn_RDX, IRDB_SDK::rn_EDX, IRDB_SDK::rn_DX, IRDB_SDK::rn_DL, IRDB_SDK::rn_DH);
+	ret_if_free5(IRDB_SDK::rn_RBX, IRDB_SDK::rn_EBX, IRDB_SDK::rn_BX, IRDB_SDK::rn_BL, IRDB_SDK::rn_BH);
+	ret_if_free5(IRDB_SDK::rn_RSI, IRDB_SDK::rn_ESI, IRDB_SDK::rn_SI, IRDB_SDK::rn_SIL, IRDB_SDK::rn_SIH);
+	ret_if_free5(IRDB_SDK::rn_RDI, IRDB_SDK::rn_EDI, IRDB_SDK::rn_DI, IRDB_SDK::rn_DIL, IRDB_SDK::rn_DIH);
+	ret_if_free5(IRDB_SDK::rn_RSP, IRDB_SDK::rn_ESP, IRDB_SDK::rn_SP, IRDB_SDK::rn_SPL, IRDB_SDK::rn_SPH);
+	ret_if_free5(IRDB_SDK::rn_RBP, IRDB_SDK::rn_EBP, IRDB_SDK::rn_BP, IRDB_SDK::rn_BPL, IRDB_SDK::rn_BPH);
+	return IRDB_SDK::rn_UNKNOWN;
+}
+
+string Register::readRegisterSet(const string &in, RegisterSet_t &out)
+{
+	size_t pos=in.find("ZZ");
+	string regname;
+	stringstream ss(in);
+
+	while ( ss>>regname )
+	{
+		if( regname=="ZZ")
+			return in.substr(pos+3);
+
+		out.insert(getRegister(regname));
+	}
+
+	assert(0 && "No terminator found for register list");
+}
+
+RegisterName Register::promoteTo64(const RegisterName p_reg)
+{
+	if (is64bit(p_reg))
+		return p_reg;
+
+	switch (p_reg)
+	{
+		case IRDB_SDK::rn_AL:				
+		case IRDB_SDK::rn_AH:				
+		case IRDB_SDK::rn_AX:				
+		case IRDB_SDK::rn_EAX:
+			return IRDB_SDK::rn_RAX;
+		case IRDB_SDK::rn_BL:				
+		case IRDB_SDK::rn_BH:				
+		case IRDB_SDK::rn_BX:				
+		case IRDB_SDK::rn_EBX:
+			return IRDB_SDK::rn_RBX;
+		case IRDB_SDK::rn_CL:				
+		case IRDB_SDK::rn_CH:				
+		case IRDB_SDK::rn_CX:				
+		case IRDB_SDK::rn_ECX:
+			return IRDB_SDK::rn_RCX;
+		case IRDB_SDK::rn_DL:				
+		case IRDB_SDK::rn_DH:				
+		case IRDB_SDK::rn_DX:				
+		case IRDB_SDK::rn_EDX:
+			return IRDB_SDK::rn_RDX;
+		case IRDB_SDK::rn_DIL:
+		case IRDB_SDK::rn_DI:				
+		case IRDB_SDK::rn_EDI:
+			return IRDB_SDK::rn_RDI;
+		case IRDB_SDK::rn_SIL:
+		case IRDB_SDK::rn_SI:				
+		case IRDB_SDK::rn_ESI:
+			return IRDB_SDK::rn_RSI;
+		case IRDB_SDK::rn_BPL:
+		case IRDB_SDK::rn_BP:				
+		case IRDB_SDK::rn_EBP:
+			return IRDB_SDK::rn_RBP;
+		case IRDB_SDK::rn_SPL:
+		case IRDB_SDK::rn_SP:				
+		case IRDB_SDK::rn_ESP:
+			return IRDB_SDK::rn_RSP;
+		case IRDB_SDK::rn_R8B:
+		case IRDB_SDK::rn_R8W:
+		case IRDB_SDK::rn_R8D:
+			return IRDB_SDK::rn_R8;
+		case IRDB_SDK::rn_R9B:
+		case IRDB_SDK::rn_R9W:
+		case IRDB_SDK::rn_R9D:
+			return IRDB_SDK::rn_R9;
+		case IRDB_SDK::rn_R10B:
+		case IRDB_SDK::rn_R10W:
+		case IRDB_SDK::rn_R10D:
+			return IRDB_SDK::rn_R10;
+		case IRDB_SDK::rn_R11B:
+		case IRDB_SDK::rn_R11W:
+		case IRDB_SDK::rn_R11D:
+			return IRDB_SDK::rn_R11;
+		case IRDB_SDK::rn_R12B:
+		case IRDB_SDK::rn_R12W:
+		case IRDB_SDK::rn_R12D:
+			return IRDB_SDK::rn_R12;
+		case IRDB_SDK::rn_R13B:
+		case IRDB_SDK::rn_R13W:
+		case IRDB_SDK::rn_R13D:
+			return IRDB_SDK::rn_R13;
+		case IRDB_SDK::rn_R14B:
+		case IRDB_SDK::rn_R14W:
+		case IRDB_SDK::rn_R14D:
+			return IRDB_SDK::rn_R14;
+		case IRDB_SDK::rn_R15B:
+		case IRDB_SDK::rn_R15W:
+		case IRDB_SDK::rn_R15D:
+			return IRDB_SDK::rn_R15;
+
+		default:
+			return IRDB_SDK::rn_UNKNOWN;
+			break;
+	}
+}
+
+RegisterName Register::demoteTo32(const RegisterName p_reg)
+{
+	if (is32bit(p_reg))
+		return p_reg;
+
+	switch (p_reg)
+	{
+		case IRDB_SDK::rn_RAX:   return  IRDB_SDK::rn_EAX;
+		case IRDB_SDK::rn_RBX:   return  IRDB_SDK::rn_EBX;
+		case IRDB_SDK::rn_RCX:   return  IRDB_SDK::rn_ECX;
+		case IRDB_SDK::rn_RDX:   return  IRDB_SDK::rn_EDX;
+		case IRDB_SDK::rn_RBP:   return  IRDB_SDK::rn_EBP;
+		case IRDB_SDK::rn_RSP:   return  IRDB_SDK::rn_ESP;
+		case IRDB_SDK::rn_RSI:   return  IRDB_SDK::rn_ESI;
+		case IRDB_SDK::rn_RDI:   return  IRDB_SDK::rn_EDI;
+		case  IRDB_SDK::rn_R8:   return  IRDB_SDK::rn_R8D;
+		case  IRDB_SDK::rn_R9:   return  IRDB_SDK::rn_R9D;
+		case IRDB_SDK::rn_R10:   return IRDB_SDK::rn_R10D;
+		case IRDB_SDK::rn_R11:   return IRDB_SDK::rn_R11D;
+		case IRDB_SDK::rn_R12:   return IRDB_SDK::rn_R12D;
+		case IRDB_SDK::rn_R13:   return IRDB_SDK::rn_R13D;
+		case IRDB_SDK::rn_R14:   return IRDB_SDK::rn_R14D;
+		case IRDB_SDK::rn_R15:   return IRDB_SDK::rn_R15D;
+		default:
+			return IRDB_SDK::rn_UNKNOWN;
+			break;
+	}
+}
+
+RegisterName Register::demoteTo16(const RegisterName p_reg)
+{
+	if (is16bit(p_reg))
+		return p_reg;
+
+	switch (p_reg)
+	{
+		case IRDB_SDK::rn_RAX: case  IRDB_SDK::rn_EAX:   return IRDB_SDK::rn_AX;
+		case IRDB_SDK::rn_RBX: case  IRDB_SDK::rn_EBX:   return IRDB_SDK::rn_BX;
+		case IRDB_SDK::rn_RCX: case  IRDB_SDK::rn_ECX:   return IRDB_SDK::rn_CX;
+		case IRDB_SDK::rn_RDX: case  IRDB_SDK::rn_EDX:   return IRDB_SDK::rn_DX;
+		case IRDB_SDK::rn_RBP: case  IRDB_SDK::rn_EBP:   return IRDB_SDK::rn_BP;
+		case IRDB_SDK::rn_RSP: case  IRDB_SDK::rn_ESP:   return IRDB_SDK::rn_SP;
+		case IRDB_SDK::rn_RSI: case  IRDB_SDK::rn_ESI:   return IRDB_SDK::rn_SI;
+		case IRDB_SDK::rn_RDI: case  IRDB_SDK::rn_EDI:   return IRDB_SDK::rn_DI;
+		case  IRDB_SDK::rn_R8: case  IRDB_SDK::rn_R8D:   return IRDB_SDK::rn_R8W;
+		case  IRDB_SDK::rn_R9: case  IRDB_SDK::rn_R9D:   return IRDB_SDK::rn_R9W;
+		case IRDB_SDK::rn_R10: case IRDB_SDK::rn_R10D:   return IRDB_SDK::rn_R10W;
+		case IRDB_SDK::rn_R11: case IRDB_SDK::rn_R11D:   return IRDB_SDK::rn_R11W;
+		case IRDB_SDK::rn_R12: case IRDB_SDK::rn_R12D:   return IRDB_SDK::rn_R12W;
+		case IRDB_SDK::rn_R13: case IRDB_SDK::rn_R13D:   return IRDB_SDK::rn_R13W;
+		case IRDB_SDK::rn_R14: case IRDB_SDK::rn_R14D:   return IRDB_SDK::rn_R14W;
+		case IRDB_SDK::rn_R15: case IRDB_SDK::rn_R15D:   return IRDB_SDK::rn_R15W;
+		default:
+			return IRDB_SDK::rn_UNKNOWN;
+			break;
+	}
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/MEDS_SafeFuncAnnotation.cpp b/irdb-lib/libMEDSannotation/src/MEDS_SafeFuncAnnotation.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..de7af940b984d1d2daf2694bdaf419f9c962f5d2
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/MEDS_SafeFuncAnnotation.cpp
@@ -0,0 +1,132 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+
+#include <iostream>
+#include <cstdio>
+#include <string>
+#include <string.h>
+
+#include "MEDS_Register.hpp"
+#include "MEDS_SafeFuncAnnotation.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+
+
+
+
+MEDS_SafeFuncAnnotation::MEDS_SafeFuncAnnotation(const string &p_rawLine)
+{
+	init();
+	m_rawInputLine=p_rawLine;
+	setLeaf(false);
+	setHasFramePointer(true);
+	parse();
+}
+
+void MEDS_SafeFuncAnnotation::init()
+{
+	MEDS_FuncAnnotation::init();
+}
+
+
+/*
+	Example format (as of July 31, 2014 ) -- subject to change:
+
+    400448     24 FUNC GLOBAL .init_proc FUNC_UNSAFE NOFP RET     40045f
+    400470      6 FUNC GLOBAL .__stack_chk_fail FUNC_UNSAFE NOFP NORET FUNC_LEAF     400475
+    400480      6 FUNC GLOBAL .__libc_start_main FUNC_UNSAFE NOFP RET FUNC_LEAF     400485
+    400490      6 FUNC GLOBAL .__printf_chk FUNC_UNSAFE NOFP RET FUNC_LEAF     400495
+
+*/
+void MEDS_SafeFuncAnnotation::parse()
+{
+
+	if (m_rawInputLine.find("FUNC ")==string::npos)
+                return;
+
+        if (m_rawInputLine.find("FUNC GLOBAL")==string::npos &&
+            m_rawInputLine.find("FUNC LOCAL")==string::npos )
+	{
+		/* FUNC line that's not local or global?  I'm confused. */
+		/* could be a FUNC PROBLEM line */
+		return;
+	}
+
+        // get offset
+        VirtualOffset vo(m_rawInputLine);
+        m_virtualOffset = vo;
+
+        size_t func_name_start_pos=0, pos=0;
+        if ((pos=m_rawInputLine.find("FUNC GLOBAL"))!=string::npos)
+		func_name_start_pos=pos+strlen("FUNC GLOBAL ");
+        else if ((pos=m_rawInputLine.find("FUNC LOCAL"))!=string::npos)
+		func_name_start_pos=pos+strlen("FUNC LOCAL ");
+
+        size_t func_end_pos=m_rawInputLine.find(" ", func_name_start_pos);
+        assert(func_end_pos!=string::npos);
+        string func_name=m_rawInputLine.substr(func_name_start_pos, func_end_pos-func_name_start_pos);
+
+	// cout<<"Found safe func name='"<<func_name<<"'"<<endl;
+
+        // get offset
+        setFuncName(func_name);
+
+
+        if (m_rawInputLine.find(" FUNC_SAFE ")!=string::npos)
+	{
+		if(getenv("VERBOSE"))
+			cout<<"Found FUNC_SAFE annotation for "<<vo.to_string()<<endl;
+		markSafe();	 // sets valid
+	}
+        else if (m_rawInputLine.find(" FUNC_UNSAFE ")!=string::npos)
+	{
+		if(getenv("VERBOSE"))
+			cout<<"Found FUNC_UNSAFE annotation for "<<vo.to_string()<<endl;
+		markUnsafe();	 // sets valid
+	}
+
+        if (m_rawInputLine.find(" FUNC_LEAF ")!=string::npos)
+	{
+		if(getenv("VERBOSE"))
+			cout<<"Found FUNC_LEAF for "<<vo.to_string()<<endl;
+		setLeaf(true);
+	}
+	else
+	{
+		setLeaf(false);
+	}
+
+        if (m_rawInputLine.find(" NOFP ")!=string::npos)
+	{
+		if(getenv("VERBOSE"))
+			cout<<"Found NOFP (no frame pointer) for "<<vo.to_string()<<endl;
+		setHasFramePointer(false);
+	}
+	else
+	{
+		setHasFramePointer(true);
+	}
+
+}
+
diff --git a/irdb-lib/libMEDSannotation/src/Makefile.in b/irdb-lib/libMEDSannotation/src/Makefile.in
new file mode 100644
index 0000000000000000000000000000000000000000..352725e672c9b0b3ac708cb0103cf6b7bfe9e4a6
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/Makefile.in
@@ -0,0 +1,20 @@
+
+
+CC=@CC@
+CXX=@CXX@
+
+LIB=../lib/libMEDSannotation.a
+
+OBJS=VirtualOffset.o MEDS_Register.o MEDS_AnnotationParser.o MEDS_InstructionCheckAnnotation.o MEDS_SafeFuncAnnotation.o MEDS_ProblemFuncAnnotation.o MEDS_FRSafeAnnotation.o FuncExitAnnotation.o MEDS_FPTRShadowAnnotation.o MEDS_FuncPrototypeAnnotation.o
+
+all: $(OBJS)
+
+$(OBJS): ../include/*.hpp 
+
+clean:
+	rm -f $(OBJS) *.o 
+
+.cpp.o:
+	$(CXX) -g -c -I. -I../include $<
+	ar rc $(LIB) $@
+	cp $(LIB) ../../lib
diff --git a/irdb-lib/libMEDSannotation/src/VirtualOffset.cpp b/irdb-lib/libMEDSannotation/src/VirtualOffset.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1e4ca4f6442438a4de9ec91f326e9c3e4aa25859
--- /dev/null
+++ b/irdb-lib/libMEDSannotation/src/VirtualOffset.cpp
@@ -0,0 +1,91 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <cstdio>
+#include <iostream>
+
+#include "VirtualOffset.hpp"
+
+using namespace std;
+using namespace MEDS_Annotation;
+
+VirtualOffset::VirtualOffset()
+{
+	m_offset = 0;
+	m_libraryName = std::string(DEFAULT_LIBRARY_NAME);
+}
+
+VirtualOffset::VirtualOffset(const std::string &p_offset, const std::string &p_libraryName)
+{
+	sscanf(p_offset.c_str(), "%llx", &m_offset);
+	m_libraryName = p_libraryName;
+}
+
+VirtualOffset::VirtualOffset(const std::string &p_offset)
+{
+	sscanf(p_offset.c_str(), "%llx", &m_offset);
+	m_libraryName = std::string(DEFAULT_LIBRARY_NAME);
+}
+
+VirtualOffset::VirtualOffset(const int p_offset)
+{
+	m_offset = p_offset;
+	m_libraryName = std::string(DEFAULT_LIBRARY_NAME);
+}
+
+ApplicationAddress VirtualOffset::getOffset() const
+{
+	return m_offset;
+}
+
+std::string VirtualOffset::getLibraryName() const
+{
+	return m_libraryName;
+}
+
+bool VirtualOffset::operator < (const VirtualOffset &p_other) const
+{
+	if (&p_other == this) return false;
+	return m_offset < p_other.getOffset();
+}
+
+bool VirtualOffset::operator == (const VirtualOffset &p_other) const
+{
+	if (&p_other == this) 
+		return true;
+	else
+	{
+		return (m_offset == p_other.getOffset() && m_libraryName == p_other.getLibraryName());
+	}
+}
+
+VirtualOffset& VirtualOffset::operator = (const VirtualOffset &p_other) 
+{
+	if (&p_other == this)
+	{
+		return *this;
+	}
+	else
+	{
+		m_offset = p_other.getOffset();
+		m_libraryName = p_other.getLibraryName();
+		return *this;
+	}
+}
diff --git a/irdb-lib/libStructDiv/SConscript b/irdb-lib/libStructDiv/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..8b38ac43f269caea3edfc01cb1863e5ffdbc1a49
--- /dev/null
+++ b/irdb-lib/libStructDiv/SConscript
@@ -0,0 +1,10 @@
+import os
+
+Import('env')
+
+
+lib1=SConscript("src/SConscript")
+#lib2=SConscript("test/SConscript")
+
+rets = [ lib1 ]
+Return('rets')
diff --git a/irdb-lib/libStructDiv/SConstruct b/irdb-lib/libStructDiv/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..4d6381b5999d3e6d4e4687fc95f444ea2c4c5747
--- /dev/null
+++ b/irdb-lib/libStructDiv/SConstruct
@@ -0,0 +1,8 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+
+Return(lib)
diff --git a/irdb-lib/libStructDiv/include/filebased.h b/irdb-lib/libStructDiv/include/filebased.h
new file mode 100644
index 0000000000000000000000000000000000000000..0c6cbd0bae792fd090cd4c72c49d9793169853c9
--- /dev/null
+++ b/irdb-lib/libStructDiv/include/filebased.h
@@ -0,0 +1,30 @@
+#ifndef sd_filebased_h
+#define sd_filebased_h
+
+#include <string>
+#include <structured_diversity.h>
+
+namespace libStructDiv
+{
+
+using namespace std;
+
+
+class FileBased_StructuredDiversity_t : public StructuredDiversity_t
+{
+	public:
+
+		FileBased_StructuredDiversity_t(string key, int varid, int total_variants, string p_config);
+
+
+	protected:
+		virtual vector<string> DoBarrier(string value);	
+
+		string m_shared_dir;
+		int m_barrier_count;
+	
+};
+
+}
+
+#endif
diff --git a/irdb-lib/libStructDiv/include/libStructDiv.h b/irdb-lib/libStructDiv/include/libStructDiv.h
new file mode 100644
index 0000000000000000000000000000000000000000..d643a2a135634806cc4e050736d26f9ecbb0dd03
--- /dev/null
+++ b/irdb-lib/libStructDiv/include/libStructDiv.h
@@ -0,0 +1,6 @@
+#ifndef SD_STRUCTDIV_H
+#define SD_STRUCTDIV_H
+
+#include <structured_diversity.h>
+
+#endif
diff --git a/irdb-lib/libStructDiv/include/structured_diversity.h b/irdb-lib/libStructDiv/include/structured_diversity.h
new file mode 100644
index 0000000000000000000000000000000000000000..a6eddd8e7c5b86e804d0fff4de6ba0153e973403
--- /dev/null
+++ b/irdb-lib/libStructDiv/include/structured_diversity.h
@@ -0,0 +1,81 @@
+#ifndef SD_SDBASE_H
+#define SD_SDBASE_H
+
+#include <string>
+#include <vector>
+#include <assert.h>
+#include <sstream>
+
+namespace libStructDiv
+{
+
+using namespace std;
+
+
+class StructuredDiversity_t
+{
+	public:
+
+		// STatic factory
+		static StructuredDiversity_t* factory(string key, string p_ipc_config);
+
+	
+		// cannot use directly since there are abstract methods.
+		// use from children classes.
+		StructuredDiversity_t(string p_key, int p_variant_num, int p_total_variants) : 
+			m_variant_num(p_variant_num), m_total_variants(p_total_variants), m_key(p_key)
+		{
+			// nothing else to do.
+		}
+		virtual ~StructuredDiversity_t() { } 
+
+
+		// Perform a barrier of type T.  T should be marshable
+		// via the << and >> operators.  To avoid this, the caller can self-marshal 
+		// (Will recommends a protocol buffer package for self-marshalling)
+		// and invoke Barrier with a string.
+		template<class T> vector<T> Barrier(T value)
+		{
+        		/* marshal value into stream s */
+        		stringstream s;
+        		s<<value;
+		
+        		// pass marshalled value to DoBarrier
+        		const vector<string> &string_res=DoBarrier(s.str());
+		
+        		assert((size_t)string_res.size()==(size_t)m_total_variants);
+		
+        		/* declare a result */
+        		vector<T> t_res;
+		
+        		// for each item 
+        		for(int i=0;i<m_total_variants;i++)
+        		{
+                		stringstream t;
+                		T res;
+                		t.str(string_res[i]);
+                		t>>res;
+                		t_res.push_back(res);
+        		}
+		
+        		return t_res;
+		}
+
+
+
+		// Getters that most cfar things will need.
+		int GetVariantID() const { return m_variant_num; }
+		int GetNumberOfVariants() const { return m_total_variants; }
+		string GetKey() const { return m_key; }
+
+	protected:
+		virtual vector<string> DoBarrier(string value)=0;
+
+		int m_variant_num;
+		int m_total_variants;
+		string m_key;
+	
+};
+
+}
+#endif
diff --git a/irdb-lib/libStructDiv/src/SConscript b/irdb-lib/libStructDiv/src/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..11fce4d5b8a15fa99b3a6044b971a5bbbd3616c2
--- /dev/null
+++ b/irdb-lib/libStructDiv/src/SConscript
@@ -0,0 +1,24 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+files="filebased.cpp  structured_diversity.cpp"
+
+cpppath='''
+         $SECURITY_TRANSFORMS_HOME/libStructDiv/include/
+        '''
+
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CXXFLAGS="-fPIC")
+lib=myenv.SharedLibrary("StructDiv",  Split(files))
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/libStructDiv/src/SConstruct b/irdb-lib/libStructDiv/src/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..c96332f0422ad5df0853931209219d9a2e20bc17
--- /dev/null
+++ b/irdb-lib/libStructDiv/src/SConstruct
@@ -0,0 +1,6 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
diff --git a/irdb-lib/libStructDiv/src/filebased.cpp b/irdb-lib/libStructDiv/src/filebased.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..78b50f0a28068d688843eebe860ddb4042447497
--- /dev/null
+++ b/irdb-lib/libStructDiv/src/filebased.cpp
@@ -0,0 +1,165 @@
+
+
+#include <string>
+#include <structured_diversity.h>
+#include <filebased.h>
+#include <fstream>
+#include <iostream>
+#include <stdlib.h>
+
+
+
+#if defined(__linux__)
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
+#endif
+
+using namespace std;
+using namespace libStructDiv;
+
+
+template <class T>
+void ignore_result(T /* res */ ) {}
+
+
+template<typename T> std::string toString(const T& value)
+{
+    std::ostringstream oss;
+    oss << value;
+    return oss.str();
+}
+
+
+FileBased_StructuredDiversity_t::FileBased_StructuredDiversity_t(string key, int varid, int total_variants, string p_config)
+		: StructuredDiversity_t(key, varid, total_variants), m_barrier_count(0)
+{
+
+	assert(varid>=0 && varid<total_variants);
+
+#if defined(__linux__)
+	char* uname = getenv("USER");
+	if(!uname) {
+		uname = getenv("USERNAME");
+	}
+	if(!uname) {
+		uname = getlogin();
+	}
+	// assume p_config, which previously started with "dir://" already has the protocol stripped.
+	m_shared_dir=p_config;
+
+	// check path exists.
+	struct stat info = {};
+	if( stat(m_shared_dir.c_str(), &info ) != 0 )
+	{
+		// dir doesn't exist, make it.
+		if(mkdir(m_shared_dir.c_str(),0755)!=0)
+		{
+			// OK if this fails, because maybe another variant did it since we last checked.
+		}	
+	}
+
+	// but now, _we_ have tried to make the dir, and so it should be there, or we give up.
+	if( stat(m_shared_dir.c_str(), &info ) != 0 )
+	{
+		// at this point, we tried to make it and couldn't.
+		// and no one else did either.  Thus, it's an error.
+		perror("FileBased_StructuredDiversity_t::FileBased_StructuredDiversity_t");
+		cerr<<"Cannot create dir:"<<m_shared_dir<<endl;
+		exit(1);
+	}
+
+	if(!S_ISDIR(info.st_mode))
+	{
+		cerr<<"FileBased_StructuredDiversity_t::FileBased_StructuredDiversity_t: "
+		    <<m_shared_dir<<" is not a directory."<<endl;
+		exit(1);
+		
+	}
+
+	
+	// dir exists,
+	// remove any old Barriers file for my variant..
+	string base_filespec=m_shared_dir+"/Barriers_"+uname+"_"+GetKey()+"_*_"+toString(GetVariantID())+".*";
+	string rm_cmd="/bin/rm -f "+base_filespec;
+	int res=system(rm_cmd.c_str());
+	if(res!=0)
+	{
+		perror("FileBased_StructuredDiversity_t::FileBased_StructuredDiversity_t");
+		cerr<<"Cannot remove files, cmd="<<rm_cmd<<endl;
+		exit(1);
+	}
+		
+	cout<<"Initing shared path: "<<m_shared_dir<<endl<<"Contents:"<<endl;
+	string ls_cmd="ls "+m_shared_dir;
+	ignore_result(system(ls_cmd.c_str()));
+#else
+	assert(0); // filesystem sharing not implement on non-linux platforms yet
+#endif
+
+}
+
+
+static bool fexists(const char *filename) {
+  ifstream ifile(filename);
+  return (!!ifile);
+}
+
+vector<string> FileBased_StructuredDiversity_t::DoBarrier(string value)
+{
+	char* uname = getenv("USER");
+	if(!uname) {
+		uname = getenv("USERNAME");
+	}
+#if defined(__linux__)
+	if(!uname) {
+		uname = getlogin();
+	}
+#endif
+	assert(uname);
+	string base_filename=m_shared_dir+"/Barriers_"+uname+"_"+GetKey()+"_"+toString(m_barrier_count)+"_"+toString(GetVariantID());
+	string data_filename=base_filename+".data";
+	string done_filename=base_filename+".done";
+
+	vector<string> vres;
+
+	cout<<"Writing shared (base) filename: "<<base_filename<<endl;
+
+
+	ofstream data_file(data_filename.c_str()); 
+	if(!data_file) 
+		assert(0);
+	data_file<<value;
+	data_file.close();
+
+	ofstream done_file(done_filename.c_str()); 
+	if(!done_file) 
+		assert(0);
+	done_file<<1;
+	done_file.close();
+
+	for(int i=0;i<GetNumberOfVariants();i++)
+	{
+		string var_base_filename=m_shared_dir+"/Barriers_"+uname+"_"+GetKey()+"_"+toString(m_barrier_count)+"_"+toString(i);
+		string var_data_filename=var_base_filename+".data";
+		string var_done_filename=var_base_filename+".done";
+
+		cout<<"Waiting for shared (base) filename: "<<var_base_filename<<endl;
+
+		while(!fexists(var_done_filename.c_str()))
+			sleep(1);
+
+		ifstream infile(var_data_filename.c_str());
+		string res;
+		infile>>res;
+		infile.close();
+		vres.push_back(res);
+	}
+
+	// next time, we'll use different file names.
+	m_barrier_count++;
+
+	return vres;
+}
+
+
diff --git a/irdb-lib/libStructDiv/src/structured_diversity.cpp b/irdb-lib/libStructDiv/src/structured_diversity.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d5b41905b1b11c7eed40751d752002ca30943e4c
--- /dev/null
+++ b/irdb-lib/libStructDiv/src/structured_diversity.cpp
@@ -0,0 +1,67 @@
+
+
+#include <string>
+#include <sstream>
+#include <iostream>
+#include <stdlib.h>
+#include <assert.h>
+
+#include <libStructDiv.h>
+#include <filebased.h>
+
+
+using namespace std;
+using namespace libStructDiv;
+
+static string get_next_field(string& input, string delim, bool& success)
+{
+	success=false;
+
+	size_t pos=input.find(delim, 0);
+
+	if(pos==string::npos)
+		return string();	// report failure.
+
+	string rest=input.substr(pos+delim.length());
+	string beginning=input.substr(0,pos);
+
+
+	input=rest;     // set output parameter.
+	success=true;	// report success.
+	return beginning; 	// return the field we parsed out.
+}
+
+
+StructuredDiversity_t* StructuredDiversity_t::factory(string key, string p_ipc_config)
+{
+	string parse_string=p_ipc_config;
+	bool success=true;
+	string var_id=get_next_field(parse_string,":", success);
+	if(!success) { cout<<"cannot parse variant id from "<<p_ipc_config<<".  Expected format: var_id:tot_vars:url"<<endl;exit(1);}
+	string tot_vars=get_next_field(parse_string,":", success);
+	if(!success) { cout<<"cannot parse total # of variants from "<<p_ipc_config<<".  Expected format: var_id:tot_vars:url"<<endl;exit(1);}
+	string protocol_type=get_next_field(parse_string,"://", success);
+	if(!success) { cout<<"cannot protocol from "<<p_ipc_config<<".  Expected format: var_id:tot_vars:protocol://path"<<endl;exit(1);}
+	string config=parse_string;
+
+
+	cout<<"Varid: "<<var_id<<endl;
+	cout<<"Total Variants: "<<tot_vars<<endl;
+	cout<<"Protocol Type: '"<<protocol_type<<"'"<<endl;
+	cout<<"config: "<<config<<endl;
+
+	if(protocol_type=="dir")
+	{
+		return new FileBased_StructuredDiversity_t(key, strtoul(var_id.c_str(),0,0), strtoul(tot_vars.c_str(),0,0), config);
+	}
+	else
+	{
+		cerr<<"Cannot parse '"<<protocol_type<<"' k into a protocol name."<<endl;
+		exit(1);
+	}
+
+	
+
+
+}
+
diff --git a/irdb-lib/libStructDiv/test/SConscript b/irdb-lib/libStructDiv/test/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..bb0d3ecc9d7f465928e0125101d5e792f9ec5279
--- /dev/null
+++ b/irdb-lib/libStructDiv/test/SConscript
@@ -0,0 +1,33 @@
+import os
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+installed=[] 
+if 'build_tools' not in myenv or myenv['build_tools'] is None or int(myenv['build_tools']) == 1:
+
+	cpppath=''' 
+		 $SECURITY_TRANSFORMS_HOME/libStructDiv/include 
+		'''
+
+	LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+	LIBS=Split( "StructDiv" )
+
+	# add cpp path
+	myenv=myenv.Clone(CPPPATH=Split(cpppath))
+
+
+	pgms="simple_sd_driver"
+	for i in Split(pgms):
+		print "building "+str(i)
+		pgm=myenv.Program(target=i+".exe",  source=Split(i+".cpp"), LIBPATH=LIBPATH, LIBS=LIBS)
+		install=myenv.Install("$SECURITY_TRANSFORMS_HOME/libStructDiv/test/", pgm)
+		Default(install)
+		installed=installed+[install]
+
+
+		
+		
+Return('installed')
diff --git a/irdb-lib/libStructDiv/test/SConstruct b/irdb-lib/libStructDiv/test/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..c96332f0422ad5df0853931209219d9a2e20bc17
--- /dev/null
+++ b/irdb-lib/libStructDiv/test/SConstruct
@@ -0,0 +1,6 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
diff --git a/irdb-lib/libStructDiv/test/simple_sd_driver.cpp b/irdb-lib/libStructDiv/test/simple_sd_driver.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..2b9f3f4f8bed365b0fda70f53b80a9aeb54c211e
--- /dev/null
+++ b/irdb-lib/libStructDiv/test/simple_sd_driver.cpp
@@ -0,0 +1,54 @@
+
+#include <libStructDiv.h>
+
+#include <iostream>
+#include <stdlib.h>
+#include <libgen.h>
+
+
+using namespace std;
+using namespace libStructDiv;
+
+
+
+template<class t> void print_res(int round, StructuredDiversity_t* p, const vector<t> &res)
+{
+	for(int i=0;i<res.size();i++)
+		cout<<"round="<<round<<" myid="<<p->GetVariantID()<<":res["<<i<<"]="<<res[i]<<endl;
+}
+
+int main(int argc, char* argv[])
+{
+	if(argc!=2)
+	{
+		cerr<<"Usage: "<<argv[0]<<" varId:totVars:url"<<endl;
+		exit(1);
+	}
+
+	StructuredDiversity_t* p=StructuredDiversity_t::factory(basename(argv[0]), argv[1]);
+
+	int sign=1;
+	if(p->GetVariantID()==1)
+		sign=-sign;
+
+	for(int i=1;i<10;i++)
+	{
+
+		if( i&1 ) 
+		{
+			const vector<double> &res=p->Barrier<double>((3.14+i)*sign);
+			print_res(i,p,res);
+		}
+		else
+		{
+			const vector<int> &res=p->Barrier<int>(i *sign );	
+			print_res(i,p,res);
+		}
+
+	}
+
+
+	delete p;
+
+	return 0;
+}
diff --git a/irdb-lib/manifest.txt b/irdb-lib/manifest.txt
new file mode 100644
index 0000000000000000000000000000000000000000..e0a42281f4ea89962b20b74251e882ecfc31397d
--- /dev/null
+++ b/irdb-lib/manifest.txt
@@ -0,0 +1,6 @@
+
+directory plugins_install ps
+directory lib ps
+directory bin ps
+directory lib ps
+
diff --git a/irdb-lib/meds2pdb/SConscript b/irdb-lib/meds2pdb/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..ca7f560339534ff8749ed39cf64c61fe4aa62cff
--- /dev/null
+++ b/irdb-lib/meds2pdb/SConscript
@@ -0,0 +1,34 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+cpppath=''' 
+	 $IRDB_SDK/include 
+	 $SECURITY_TRANSFORMS_HOME/include 
+	 $SECURITY_TRANSFORMS_HOME/libIRDB-core/include 
+	 $SECURITY_TRANSFORMS_HOME/libEXEIO/include 
+	 $SECURITY_TRANSFORMS_HOME/libMEDSannotation/include 
+	'''
+
+files=Glob( Dir('.').srcnode().abspath+"/*.cpp") + Glob(Dir('.').srcnode().abspath+"/*.c")
+
+
+pgm="meds2pdb"
+
+myenv.Append(CXXFLAGS = " -std=c++11 ")
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split(" irdb-cfg irdb-util irdb-transform EXEIO MEDSannotation "+env.subst('$BASE_IRDB_LIBS')) 
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+pgm=myenv.Program(pgm,  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+install1=myenv.Install("$SECURITY_TRANSFORMS_HOME/bin/", pgm)
+install2=myenv.Install("$SECURITY_TRANSFORMS_HOME/tools/meds2pdb/", pgm)
+
+Default(install1)
+Default(install2)
+
+install=[]+install1+install2
+Return('install')
diff --git a/irdb-lib/meds2pdb/SConstruct b/irdb-lib/meds2pdb/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..17f632b8c29cd420163897b1eb044ca3486df362
--- /dev/null
+++ b/irdb-lib/meds2pdb/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+install=SConscript("SConscript")
+Return('install')
diff --git a/irdb-lib/meds2pdb/aspri.h b/irdb-lib/meds2pdb/aspri.h
new file mode 100644
index 0000000000000000000000000000000000000000..0da73ac38278996f05b96385b1601619145e8327
--- /dev/null
+++ b/irdb-lib/meds2pdb/aspri.h
@@ -0,0 +1,41 @@
+/*
+ * aspri.h - main SPRI header file
+ *
+ * Copyright (c) 2000, 2001, 2010, 2011 - Zephyr Software
+ *
+ * This file is part of the Strata dynamic code modification infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+/*
+ * aspri.h
+ * author: Jason Hiser, Anh Nguyen-Tuong
+ */
+
+#ifndef aspri_h
+#define aspri_h
+
+typedef struct aspri_address aspri_address_t;
+struct aspri_address
+{
+	char *library_name;
+	VirtualOffset_t offset;
+	bool isCurrentPC;
+};
+
+#endif
diff --git a/irdb-lib/meds2pdb/bitvector.cpp b/irdb-lib/meds2pdb/bitvector.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e3c627724516c9570e1b49a364595222cbac4fe8
--- /dev/null
+++ b/irdb-lib/meds2pdb/bitvector.cpp
@@ -0,0 +1,151 @@
+/*
+ * bitvector.c - bit vector routines.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+/* bitvector.c
+ *
+ * Author: mc2zk
+ * Description:  bit vector implementation using chars
+ */
+
+
+#include "meds_all.h"
+
+
+/* 
+ * allocate memory for the bitvector given number of 
+ * bit fields, number of data chunks 
+ */
+bitvector_t * allocate_bitvector(int num_fields, int num_data_chunks)
+{
+	/* round number of bits up to 8 then convert to bytes */
+	int num_bytes_to_allocate=(((num_fields*num_data_chunks) + 7) &~7)/8;
+
+	bitvector_t * the_bitvector = (bitvector_t*)spri_allocate_type(sizeof(bitvector_t));
+	/* allocate the_bits 
+	 *  	the number of bits needed is num_fields * num_data_chunks 
+	 * 	rounded to nearest 8 (num bits in a char)
+	 * 	to get bytes, need to divide by 8 bits
+ 	 */
+	the_bitvector->the_bits = (char*)spri_allocate_type(num_bytes_to_allocate*sizeof(char));
+	the_bitvector->size = num_fields*num_data_chunks;
+	the_bitvector->num_bytes = num_bytes_to_allocate;
+
+	return the_bitvector;
+}
+
+/* reclaim the allocated memory */
+void free_bitvector(bitvector_t *the_bitvector_to_be_freed)
+{
+#ifndef NDEBUG
+// 	STRATA_LOG("profile_fields_allocate","bitvector address:  0x%x size: %d\n", the_bitvector_to_be_freed, the_bitvector_to_be_freed->size);
+#endif
+	/* first free the_bits vector */
+	spri_deallocate_type((void *)the_bitvector_to_be_freed->the_bits, ((the_bitvector_to_be_freed->size+7)&~7)/8);
+
+	/* then free the bitvector_t memory */
+	spri_deallocate_type((void *)the_bitvector_to_be_freed, sizeof(bitvector_t));
+
+}
+
+/* set the bit to 1 */
+void set_bitvector(bitvector_t *the_vector, int the_bit_to_set){
+
+	/* check to make sure that the bounds are not being exceeded */
+	if(the_vector &&(the_bit_to_set >= the_vector->size))
+	{
+		/* don't set the bit if out of bounds */
+		return;
+	}
+	the_vector->the_bits[the_bit_to_set >> 3] |= 1 << (the_bit_to_set & 7);
+}
+
+/* clear the bit */
+void clear_bit(bitvector_t *the_vector, int the_bit_to_clear){
+	the_vector->the_bits[the_bit_to_clear >> 3] &= ~(1 << (the_bit_to_clear & 7));
+}
+
+
+/* get a bit from the bit vector: returns 1 if bit is 1, 0 if bit is 0 */
+char get_bit(bitvector_t *the_vector, int the_bit){
+	return (the_vector->the_bits[the_bit >> 3] & (1 << (the_bit & 7))) !=0;
+
+}
+
+/* function to print the bit vector in hexadecimal */
+void print_bitvector_hex(FILE * fout, bitvector_t *the_vector)
+{
+	int i=0;
+	int num_elems_in_bytes=the_vector->num_bytes;
+
+	/* how many elements should be in the int array? */
+	int num_elems_in_int=(num_elems_in_bytes+3)/4 /* bytes per int */;
+
+	/* print out the number of elements in the integer array */
+	fprintf(fout, "%d %d ", the_vector->size, num_elems_in_int);
+
+	/* convert to int array */
+	/* iterate through bitvector and populate intArray */
+	for(i=0; i<num_elems_in_bytes; i+=sizeof(int))
+	{
+		fprintf(fout, "%x ", *(int*)(&the_vector->the_bits[i]));
+	}
+
+	fprintf(fout, "\n");
+}
+
+/* print/dump the bit vector in binary */
+void print_bitvector_binary(FILE * fout, bitvector_t *the_vector)
+{
+	fprintf(fout, "%d ", the_vector->size /* size in bits */);
+
+	/* print out the bits */
+	fwrite(the_vector->the_bits, sizeof(char), the_vector->num_bytes, fout);
+
+	fprintf(fout, "\n");
+}
+
+/* print/dump the bit vector one bit at a time for debug purposes */
+void print_bitvector_bits(FILE * fout, bitvector_t *the_vector)
+{
+	int i=0;
+	fprintf(fout, "size in bits: %d \n", the_vector->size /* size in bits */);
+
+	/* print out the bits */
+	for(i=0; i < the_vector->size; i++)
+	{
+		fprintf(fout, "%d ", get_bit(the_vector, i) );
+	}
+
+	fprintf(fout, "\n");
+}
+
+
+/* find_bit_number(): Calculate the bit number in the vector to find  */
+int find_bit_number(int num_fields, int which_data_chunk, int which_field_to_get
+)
+{
+	int the_bit_number=(which_data_chunk*num_fields)+which_field_to_get;
+
+	return the_bit_number;
+}
+
diff --git a/irdb-lib/meds2pdb/bitvector.h b/irdb-lib/meds2pdb/bitvector.h
new file mode 100644
index 0000000000000000000000000000000000000000..56ad45e37e1fed077c798524751070b8db3a479e
--- /dev/null
+++ b/irdb-lib/meds2pdb/bitvector.h
@@ -0,0 +1,72 @@
+/*
+ * bitvector.h - bit vector headers.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+/* bitvector.h
+ *
+ * Author: mc2zk
+ * Description:  bit vector implementation using chars
+ */
+
+#ifndef bitvector_h
+#define bitvector_h
+
+struct bitvector
+{
+	char * the_bits;
+	int size;	/* size of the bit vector - number of bits represented */
+	int num_bytes;
+};
+typedef struct bitvector bitvector_t;
+
+
+/* 
+ * allocate memory for the bitvector given number of 
+ * bit fields, number of data chunks 
+ */
+bitvector_t * allocate_bitvector(int num_fields, int num_data_chunks);
+
+/* reclaim the allocated memory */
+void free_bitvector(bitvector_t *the_bitvector_to_be_freed);
+
+/* set the bit to 1 */
+void set_bitvector(bitvector_t *the_vector, int the_bit_to_set);
+
+/* clear the bit */
+void clear_bit(bitvector_t *the_vector, int the_bit_to_clear);
+
+/* get a bit from the bit vector */
+char get_bit(bitvector_t *the_vector, int the_bit);
+
+/* print/dump the bit vector: hexadecimal format */
+void print_bitvector_hex(FILE *fout, bitvector_t *the_vector);
+
+/* print/dump the bit vector: binary format */
+void print_bitvector_binary(FILE *fout, bitvector_t *the_vector);
+
+/* print the bit vector one bit at a time */
+void print_bitvector_bits(FILE *fout, bitvector_t *the_vector);
+
+/* find_bit_number(): Calculate the bit number in the vector to find  */
+int find_bit_number(int num_fields, int which_data_chunk, int which_field_to_get);
+
+#endif
diff --git a/irdb-lib/meds2pdb/constant_hash.cpp b/irdb-lib/meds2pdb/constant_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..368ccbeb3da3e624c8d42b24081d6c17f2f2f5b6
--- /dev/null
+++ b/irdb-lib/meds2pdb/constant_hash.cpp
@@ -0,0 +1,90 @@
+/*
+ * constant_hash.c - hashtable for contants.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include "meds_all.h"
+
+Hashtable *constants_hash=NULL;
+
+long constants_compute_hash(void* key1)
+{
+        constant_hash_key_t * a_key=(constant_hash_key_t *)key1;
+
+        return a_key->pc ^ a_key->the_const ^ (a_key->field << 4);
+}
+
+long constants_key_compare(void* key1, void* key2)
+{
+        constant_hash_key_t * a_key=(constant_hash_key_t *)key1;
+        constant_hash_key_t * b_key=(constant_hash_key_t *)key2;
+
+        if(a_key->pc == b_key->pc)
+	{
+		if(a_key->field==b_key->field)
+                	return a_key->the_const == b_key->the_const;
+		else
+        		return a_key->field == b_key->field;
+	}
+        return a_key->pc == b_key->pc;
+}
+
+
+constant_hash_value_t * add_constant_ref(VirtualOffset_t pc,int the_const, constant_hash_field_t the_field, constant_hash_type_t the_type)
+{
+        constant_hash_key_t *chk=(constant_hash_key_t*)spri_allocate_type(sizeof(constant_hash_key_t ));
+        constant_hash_value_t *chv=(constant_hash_value_t*)spri_allocate_type(sizeof(constant_hash_value_t ));
+        /* set the key */
+        chk->pc=pc;
+        chk->the_const=the_const;
+        chk->field=the_field;
+        /* set the data */
+        chv->type=the_type;
+
+        Hashtable_put(constants_hash, chk, chv);
+	return chv;
+
+}
+
+constant_hash_value_t * get_constant_ref(VirtualOffset_t pc, int the_const, constant_hash_field_t the_field)
+{
+	constant_hash_key_t chk={pc, the_const, the_field};
+	constant_hash_value_t *chv=(constant_hash_value_t*)Hashtable_get(constants_hash, &chk);
+
+        return  chv ? chv : 0;
+
+}
+
+
+const char* constant_hash_type_to_string(constant_hash_type_t type)
+{
+	switch(type)
+	{
+		case cht_ESP: 	return "PTRIMMEDESP2 STACK";
+		case cht_EBP: 	return "PTRIMMEDEBP2 STACK";
+		case cht_GLOBAL:	return "PTRIMMEDABSOLUTE GLOBAL";
+		case cht_NUMBER: 	return "NUMIMMED GLOBAL";
+		case cht_UNKNOWN:	return "UNKNOWNIMMED GLOBAL";
+		default:
+			assert(0);
+	}
+}
+
diff --git a/irdb-lib/meds2pdb/constant_hash.h b/irdb-lib/meds2pdb/constant_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..2159265286a583ab50e80984b3d908189489bb3a
--- /dev/null
+++ b/irdb-lib/meds2pdb/constant_hash.h
@@ -0,0 +1,58 @@
+/*
+ * constant_hash.h - hashtable for contants.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef constant_hash_h
+#define constant_hash_h
+
+
+enum constant_hash_type { cht_ESP, cht_EBP, cht_GLOBAL, cht_NUMBER, cht_UNKNOWN };
+typedef enum constant_hash_type constant_hash_type_t;
+enum constant_hash_field {chf_DISPLACEMENT='d', chf_IMMEDIATE='i', chf_SCALE='s', chf_IMPLICIT='m', chf_OTHER='o'};
+typedef enum constant_hash_field constant_hash_field_t;
+
+extern Hashtable *constants_hash;
+struct constant_hash_key
+{
+        VirtualOffset_t pc;
+        int the_const;
+	constant_hash_field_t field;
+};
+typedef struct constant_hash_key constant_hash_key_t;
+struct constant_hash_value
+{
+        constant_hash_type_t type;
+	int real_const;
+};
+typedef struct constant_hash_value constant_hash_value_t;
+
+long constants_compute_hash(void* key1);
+
+long constants_key_compare(void* key1, void* key2);
+
+constant_hash_value_t * add_constant_ref(VirtualOffset_t pc,int the_const, constant_hash_field_t the_field, constant_hash_type_t the_type);
+
+constant_hash_value_t * get_constant_ref(VirtualOffset_t pc, int the_const, constant_hash_field_t the_field);
+
+const char* constant_hash_type_to_string(constant_hash_type_t type);
+
+#endif
diff --git a/irdb-lib/meds2pdb/elfreader.cpp b/irdb-lib/meds2pdb/elfreader.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..51f10cecea32d236fba283975abc44cf1b47f029
--- /dev/null
+++ b/irdb-lib/meds2pdb/elfreader.cpp
@@ -0,0 +1,157 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <iostream>
+#include <string.h>
+#include <stdio.h>
+#include <irdb-core>
+#include <libIRDB-core.hpp>
+#include "elfreader.h"
+
+using namespace std;
+using namespace IRDB_SDK;
+using namespace EXEIO;
+
+ElfReader::ElfReader(char *p_elfFile)
+{
+//    m_reader=new elfio;
+	m_reader=new EXEIO::exeio(p_elfFile);
+	assert(m_reader);
+
+	EXEIO::dump::header(cout, *m_reader);
+	EXEIO::dump::section_headers(cout, *m_reader);
+
+    // Initialize it
+/*
+    bool ok = m_reader->load( p_elfFile );
+    if ( ! ok ) {
+        std::cerr << "Can't open file:" << p_elfFile << std::endl;
+	assert(0);
+	exit(-1);
+    }
+
+
+    if(m_reader->get_class() == ELFCLASS32)
+	std::cout << "Input file is ELF32" << std::endl;
+    else
+	std::cout << "Input file is ELF64" << std::endl;
+
+
+    // List all sections of the file
+    int i;
+    ELFIO::Elf_Half nSecNo = m_reader->sections.size();
+    for ( i = 0; i < nSecNo; ++i ) 
+    {    // For all sections
+	section* psec = m_reader->sections[i];
+	m_sections.push_back(psec);
+        std::cout << "  [" << i << "] "
+                  << psec->get_name()
+                  << "\t"
+                  << psec->get_size()
+                  << std::endl;
+
+    }
+    std::cout << std::endl;
+*/
+}
+
+ElfReader::~ElfReader()
+{
+  delete m_reader;
+}
+
+/*
+* Read <p_numBytes> from ELF file for location <p_pc>
+*/
+string ElfReader::read(VirtualOffset_t p_pc, unsigned p_numBytes) const
+{
+  for ( int i = 0; i < m_reader->sections.size(); ++i ) 
+  {    
+    section* pSec = m_reader->sections[i];
+    if (pSec->get_address() + pSec->get_size() < 1) continue;
+    if (p_pc >= pSec->get_address() && p_pc <= (pSec->get_address() + pSec->get_size() - 1))
+    {
+      // found the section, now read off the data
+      long offset = p_pc - pSec->get_address();
+
+      // caution!  This may result in an overflow of the section and fault if called with p_numBytes too big.
+      return string(pSec->get_data() + offset, p_numBytes);
+    }
+  }
+  return string();
+}
+
+/*
+* Read <p_numBytes> from ELF file for location <p_pc>
+* No bounds checking is done on <p_buf>
+* Return false if address not in valid sections
+*/
+bool ElfReader::read(VirtualOffset_t p_pc, unsigned p_numBytes, char* p_buf) const
+{
+  for ( int i = 0; i < m_reader->sections.size(); ++i ) 
+  {    
+    section* pSec = m_reader->sections[ i ];
+
+    if (pSec->get_address() + pSec->get_size() < 1) continue;
+    if (p_pc >= pSec->get_address() && p_pc <= (pSec->get_address() + pSec->get_size() - 1))
+    {
+      // found the section, now read off the data
+      long offset = p_pc - pSec->get_address();
+      memcpy(p_buf, pSec->get_data() + offset, p_numBytes);
+      return true;
+    }
+  }
+  return false;
+}
+
+/*
+* Return buffer for instruction off the ELF file
+*/
+const char* ElfReader::getInstructionBuffer(VirtualOffset_t p_pc) const
+{
+  for ( int i = 0; i < m_reader->sections.size(); ++i ) 
+  {    
+    const section* pSec = m_reader->sections[ i ];
+
+    if (pSec->get_address() + pSec->get_size() < 1) continue;
+    if (p_pc >= pSec->get_address() && p_pc <= (pSec->get_address() + pSec->get_size() - 1))
+    {
+      // found the section, now read off the data
+      long offset = p_pc - pSec->get_address();
+      return (char*) (pSec->get_data() + offset);
+    }
+  }
+  return NULL;
+}
+
+void ElfReader::SetArchitecture()
+{
+	const auto width =
+		(isElf32() || isPe32()) ? 32 :
+		(isElf64() || isPe64()) ? 64 :
+		throw std::invalid_argument("Unknown architecture.");
+	const auto mt = m_reader->getMachineType() == EXEIO::mtI386 ? IRDB_SDK::admtI386 :
+			m_reader->getMachineType() == EXEIO::mtX86_64 ? IRDB_SDK::admtX86_64 :
+			m_reader->getMachineType() == EXEIO::mtAarch64 ? IRDB_SDK::admtAarch64 :
+			throw std::invalid_argument("Unknown architecture.");
+
+	libIRDB::FileIR_t::setArchitecture(width,mt);
+}
+
diff --git a/irdb-lib/meds2pdb/elfreader.h b/irdb-lib/meds2pdb/elfreader.h
new file mode 100644
index 0000000000000000000000000000000000000000..87b4ac4a71b303008e96b265d1885f5828c49804
--- /dev/null
+++ b/irdb-lib/meds2pdb/elfreader.h
@@ -0,0 +1,38 @@
+#ifndef _elfreader_H_
+#define _elfreader_H_
+
+#include <vector>
+#include "exeio.h"
+#include <irdb-core>
+#include <assert.h>
+#include <exception>
+#include <irdb-core>
+
+
+// doing this is very bad.
+// using namespace std;
+// using namespace ELFIO;
+
+class ElfReader 
+{
+	public:
+
+	ElfReader(char *);
+	virtual ~ElfReader();
+
+	std::string read(IRDB_SDK::VirtualOffset_t p_pc, unsigned p_numBytes) const ;
+	bool read(IRDB_SDK::VirtualOffset_t p_pc, unsigned p_numBytes, char* p_buf) const ;
+	const char* getInstructionBuffer(IRDB_SDK::VirtualOffset_t p_pc) const ;
+
+	bool isElf32() const { assert(m_reader); return m_reader->get_class()==EXEIO::ELF32; }
+	bool isElf64() const { assert(m_reader); return m_reader->get_class()==EXEIO::ELF64; }
+	bool isPe32() const { assert(m_reader); return m_reader->get_class()==EXEIO::PE32; }
+	bool isPe64() const { assert(m_reader); return m_reader->get_class()==EXEIO::PE64; }
+	void SetArchitecture() ;
+
+  	private:
+	EXEIO::exeio*                       m_reader;
+
+};
+
+#endif
diff --git a/irdb-lib/meds2pdb/framerestore_hash.cpp b/irdb-lib/meds2pdb/framerestore_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d7c2d400fda6c41c9a0d98b81706bcb22c7a1230
--- /dev/null
+++ b/irdb-lib/meds2pdb/framerestore_hash.cpp
@@ -0,0 +1,142 @@
+/*
+ * framerestore_hash.c - how to unwind frames.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <string.h>
+#include "framerestore_hash.h"
+
+Hashtable *framerestores_hash=NULL;
+
+long framerestores_compute_hash(void* key1)
+{
+        framerestore_hash_key_t * a_key=(framerestore_hash_key_t *)key1;
+
+        return a_key->pc;
+}
+
+long framerestores_key_compare(void* key1, void* key2)
+{
+        framerestore_hash_key_t * a_key=(framerestore_hash_key_t *)key1;
+        framerestore_hash_key_t * b_key=(framerestore_hash_key_t *)key2;
+
+        return a_key->pc == b_key->pc;
+}
+
+
+/*
+ * frame_restore_set_return_address - set the offset of the return address for this frame
+ */
+void frame_restore_set_return_address(VirtualOffset_t pc, int offset)
+{
+	instrmap_hash_value_t *imhv=(instrmap_hash_value_t*)Hashtable_get(instrmaps_hash,&pc);
+
+	if(!imhv)
+		return;
+
+	framerestore_hash_value_t *frhv=(framerestore_hash_value_t*)Hashtable_get(framerestores_hash,&imhv->func_addr);
+
+	if(!frhv)
+	{
+		framerestore_hash_key_t * frhk=(framerestore_hash_key_t*)spri_allocate_type(sizeof(framerestore_hash_key_t));
+		frhv=(framerestore_hash_value_t*)spri_allocate_type(sizeof(framerestore_hash_value_t));
+		assert(frhv);
+		memset(frhv,0, sizeof(*frhv));
+
+
+		frhk->pc=imhv->func_addr;
+
+		Hashtable_put(framerestores_hash, frhk, frhv);
+	}
+
+	frhv->ret_offset=offset;
+}
+
+
+
+/* 
+ * frame_restore_hash_add_reg_restore - add info to the frame restore hash about the type and offset of saved registers
+ */
+void frame_restore_hash_add_reg_restore(VirtualOffset_t addr, int reg_num, int reg_offset, int reg_type)
+{
+
+        framerestore_hash_value_t *frhv=(framerestore_hash_value_t*) Hashtable_get(framerestores_hash,&addr);
+
+        if(!frhv)
+        {
+                framerestore_hash_key_t * frhk=(framerestore_hash_key_t*)spri_allocate_type(sizeof(framerestore_hash_key_t));
+                frhv=(framerestore_hash_value_t*)spri_allocate_type(sizeof(framerestore_hash_value_t));
+
+		assert(frhv);
+		memset(frhv,0, sizeof(*frhv));
+
+
+                frhk->pc=addr;
+
+                Hashtable_put(framerestores_hash, frhk, frhv);
+        }
+
+        frhv->reg_offsets[reg_num]=reg_offset;
+        frhv->reg_types[reg_num]=reg_type;
+
+	assert(reg_num>=0 && reg_num<=15);
+	assert(reg_type>=0 && reg_type<=255);
+	assert(reg_offset<=0);
+	
+}
+
+
+void frame_restore_hash_set_safe_bit(VirtualOffset_t addr, int is_safe)
+{
+
+        framerestore_hash_value_t *frhv=(framerestore_hash_value_t*)Hashtable_get(framerestores_hash,&addr);
+
+        if(!frhv)
+        {
+                framerestore_hash_key_t * frhk=(framerestore_hash_key_t*)spri_allocate_type(sizeof(framerestore_hash_key_t));
+                frhv=(framerestore_hash_value_t*)spri_allocate_type(sizeof(framerestore_hash_value_t));
+
+		assert(frhv);
+		memset(frhv,0, sizeof(*frhv));
+
+
+                frhk->pc=addr;
+
+                Hashtable_put(framerestores_hash, frhk, frhv);
+        }
+
+        frhv->static_analyzer_believes_safe=is_safe;
+}
+
+int is_safe_function(VirtualOffset_t pc)
+{
+	instrmap_hash_value_t *imhv=(instrmap_hash_value_t*)Hashtable_get(instrmaps_hash,&pc);
+
+	if(!imhv)
+		return FALSE;
+
+	framerestore_hash_value_t *frhv=(framerestore_hash_value_t*)Hashtable_get(framerestores_hash,&imhv->func_addr);
+
+	if(!frhv)
+		return FALSE;
+
+	return frhv->static_analyzer_believes_safe;
+}
diff --git a/irdb-lib/meds2pdb/framerestore_hash.h b/irdb-lib/meds2pdb/framerestore_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..df466ba832ce3990f077e541ef9897650ffbd4ec
--- /dev/null
+++ b/irdb-lib/meds2pdb/framerestore_hash.h
@@ -0,0 +1,61 @@
+/*
+ * framerestore_hash.h - how to unwind frames.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef framerestore_hash_h
+#define framerestore_hash_h
+
+#include "meds_all.h"
+
+
+extern Hashtable *framerestores_hash;
+struct framerestore_hash_key
+{
+        int pc;	// function address
+};
+typedef struct framerestore_hash_key framerestore_hash_key_t;
+
+struct framerestore_hash_value
+{
+	int reg_offsets[16];	/* index by MD_REG_*, 0=do not restore, else add offset to ret_addr offset */
+	int reg_types[16];	/* index by MD_REG_*, return type of each register  */
+
+	int ret_offset;
+
+	int static_analyzer_believes_safe;
+};
+
+typedef struct framerestore_hash_value framerestore_hash_value_t;
+
+long framerestores_compute_hash(void* key1);
+
+long framerestores_key_compare(void* key1, void* key2);
+
+void frame_restore_hash_add_reg_restore(VirtualOffset_t addr, int reg_num, int reg_offset, int reg_type);
+
+void frame_restore_hash_set_safe_bit(VirtualOffset_t addr, int is_safe);
+
+void frame_restore_hash_set_frame_size(VirtualOffset_t addr, int is_safe);
+void frame_restore_set_return_address(VirtualOffset_t pc, int offset);
+
+
+#endif
diff --git a/irdb-lib/meds2pdb/framesize_hash.cpp b/irdb-lib/meds2pdb/framesize_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e6f3a8de4c64fdf4bdcdaabe32cb9502f1286f5a
--- /dev/null
+++ b/irdb-lib/meds2pdb/framesize_hash.cpp
@@ -0,0 +1,61 @@
+#include "framesize_hash.h"
+
+Hashtable *framesizes_hash=NULL;
+
+long framesizes_compute_hash(void* key1)
+{
+        framesize_hash_key_t * a_key=(framesize_hash_key_t *)key1;
+
+        return a_key->pc;
+}
+
+long framesizes_key_compare(void* key1, void* key2)
+{
+        framesize_hash_key_t * a_key=(framesize_hash_key_t *)key1;
+        framesize_hash_key_t * b_key=(framesize_hash_key_t *)key2;
+
+        return a_key->pc == b_key->pc;
+}
+
+void set_frame_size(int pc, int frame_size)
+{
+	framesize_hash_key_t fshk={pc};
+	framesize_hash_value_t *fshv=(framesize_hash_value_t*)Hashtable_get(framesizes_hash, &fshk);
+
+	if(fshv)
+	{
+		if(fshv->frame_size != frame_size)
+		{
+			fshv->var_sized=TRUE;
+		}
+		return;
+	}
+
+	framesize_hash_key_t *fshk2=(framesize_hash_key_t*)spri_allocate_type(sizeof(*fshk2));
+	framesize_hash_value_t *fshv2=(framesize_hash_value_t*)spri_allocate_type(sizeof(*fshv2));
+
+	*fshk2=fshk;
+	fshv2->frame_size=frame_size;
+	fshv2->var_sized=FALSE;
+
+	Hashtable_put(framesizes_hash, fshk2, fshv2);
+
+}
+
+
+int is_var_sized_frame(int pc)
+{
+	framesize_hash_key_t fshk={pc};
+	framesize_hash_value_t *fshv=(framesize_hash_value_t*)Hashtable_get(framesizes_hash, &fshk);
+
+	if(fshv)
+	{
+		return fshv->var_sized;
+	}
+
+	/* if we didn't find it, it's not var-sized yet */
+	return FALSE;
+}
+
+
+
diff --git a/irdb-lib/meds2pdb/framesize_hash.h b/irdb-lib/meds2pdb/framesize_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..a379e485217426b6ed8c38c6a578fc8d6fec67ac
--- /dev/null
+++ b/irdb-lib/meds2pdb/framesize_hash.h
@@ -0,0 +1,29 @@
+#ifndef framesize_hash_h
+#define framesize_hash_h
+
+#include "meds_all.h"
+
+
+extern Hashtable *framesizes_hash;
+struct framesize_hash_key
+{
+        int pc;
+};
+typedef struct framesize_hash_key framesize_hash_key_t;
+
+struct framesize_hash_value
+{
+	int frame_size;
+	int var_sized;
+};
+typedef struct framesize_hash_value framesize_hash_value_t;
+
+long framesizes_compute_hash(void* key1);
+
+long framesizes_key_compare(void* key1, void* key2);
+
+void set_frame_size(int pc, int frame_size);
+int is_var_sized_frame(int pc);
+
+
+#endif
diff --git a/irdb-lib/meds2pdb/funclist_hash.cpp b/irdb-lib/meds2pdb/funclist_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..00db7aa1c0b3e6bc9494c0c47db41a46365fa0d1
--- /dev/null
+++ b/irdb-lib/meds2pdb/funclist_hash.cpp
@@ -0,0 +1,51 @@
+/*
+ * funclist_hash.c - list of functions hashtable.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <string.h>
+#include "funclist_hash.h"
+
+Hashtable *funclists_hash=NULL;
+
+long funclists_compute_hash(void* key1)
+{
+        funclist_hash_key_t * a_key=(funclist_hash_key_t *)key1;
+	char *s =a_key->name;
+
+	int h = 0;
+	while (*s)
+	{
+    		h = 31*h + *s;
+		s++;
+	}
+	return h;
+}
+
+long funclists_key_compare(void* key1, void* key2)
+{
+        funclist_hash_key_t * a_key=(funclist_hash_key_t *)key1;
+        funclist_hash_key_t * b_key=(funclist_hash_key_t *)key2;
+
+        return !strcmp(a_key->name, b_key->name);
+}
+
+
diff --git a/irdb-lib/meds2pdb/funclist_hash.h b/irdb-lib/meds2pdb/funclist_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..7e3f618e398120c2850bb46be237d09c74f65baa
--- /dev/null
+++ b/irdb-lib/meds2pdb/funclist_hash.h
@@ -0,0 +1,48 @@
+/*
+ * funclist_hash.h - list of functions hashtable.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef funclist_hash_h
+#define funclist_hash_h
+
+#include "meds_all.h"
+
+
+extern Hashtable *funclists_hash;
+struct funclist_hash_key
+{
+	char* name;
+	
+};
+typedef struct funclist_hash_key funclist_hash_key_t;
+
+struct funclist_hash_value
+{
+        int pc;
+};
+typedef struct funclist_hash_value funclist_hash_value_t;
+
+long funclists_compute_hash(void* key1);
+
+long funclists_key_compare(void* key1, void* key2);
+
+#endif
diff --git a/irdb-lib/meds2pdb/function_descriptor.cpp b/irdb-lib/meds2pdb/function_descriptor.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e81dd459c053143cb97465f05c4595cc3dd6f6c1
--- /dev/null
+++ b/irdb-lib/meds2pdb/function_descriptor.cpp
@@ -0,0 +1,142 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <string>
+#include <cstdio>
+
+#include "function_descriptor.h"
+using namespace IRDB_SDK;
+
+void wahoo::Function::_init()
+{
+  m_name = "";
+  m_address = -1;
+  m_size = -1;
+  m_frameSize = 0;
+  m_isSafe = false;
+  m_useFP = false;
+  m_outArgsRegionSize = 0;
+  m_functionID = -1;
+}
+
+wahoo::Function::Function()
+{
+  _init();
+}
+
+wahoo::Function::Function(VirtualOffset_t p_start)
+{
+  _init();
+  setAddress(p_start);
+}
+
+wahoo::Function::Function(string p_name, VirtualOffset_t p_start, int p_size)
+{
+  _init();
+  setName(p_name);
+  setAddress(p_start);
+  setSize(p_size);
+}
+
+wahoo::Function::~Function()
+{
+}
+
+bool wahoo::Function::operator == (const Function &other)
+{
+  return (other.m_name == this->m_name && other.m_address == this->m_address);
+}
+
+bool wahoo::Function::operator == (const VirtualOffset_t p_addr)
+{
+  return (this->m_address == p_addr);
+}
+
+bool wahoo::Function::operator != (const Function &other)
+{
+  return (other.m_name != this->m_name || other.m_address != this->m_address);
+}
+
+bool wahoo::Function::operator != (const VirtualOffset_t p_addr)
+{
+  return (this->m_address != p_addr);
+}
+
+void wahoo::Function::addInstruction(wahoo::Instruction* p_instr)
+{
+  m_allInstructions.push_back(p_instr);
+}
+
+void wahoo::Function::addStackAllocationInstruction(wahoo::Instruction* p_instr)
+{
+  m_stackAllocInstructions.push_back(p_instr);
+}
+
+void wahoo::Function::addStackDeallocationInstruction(wahoo::Instruction* p_instr)
+{
+  m_stackDeallocInstructions.push_back(p_instr);
+}
+
+void wahoo::Function::addStackReferenceInstruction(wahoo::Instruction* p_instr)
+{
+  m_stackRefsInstructions.push_back(p_instr);
+}
+
+vector<wahoo::Instruction*> wahoo::Function::getInstructions()
+{
+  return m_allInstructions;
+}
+
+vector<wahoo::Instruction*> wahoo::Function::getStackAllocationInstructions()
+{
+  return m_stackAllocInstructions;
+}
+
+vector<wahoo::Instruction*> wahoo::Function::getStackDeallocationInstructions()
+{
+  return m_stackDeallocInstructions;
+}
+
+vector<wahoo::Instruction*> wahoo::Function::getStackReferencesInstructions()
+{
+  return m_stackRefsInstructions;
+}
+
+double wahoo::Function::getInstructionCoverage(int *p_count, int *p_total)
+{
+  unsigned count = 0;
+  if (m_allInstructions.size() == 0)
+    return 0.0;
+  for (auto i = 0U; i < m_allInstructions.size(); ++i)
+  {
+    if (m_allInstructions[i]->isVisited())
+      count++;
+  } 
+ 
+  *p_count = count;
+  *p_total = m_allInstructions.size();
+  return (double) count / (double) m_allInstructions.size();
+}
+
+double wahoo::Function::getInstructionCoverage()
+{
+  int count, total;
+  return getInstructionCoverage(&count, &total);
+}
diff --git a/irdb-lib/meds2pdb/function_descriptor.h b/irdb-lib/meds2pdb/function_descriptor.h
new file mode 100644
index 0000000000000000000000000000000000000000..502c175e6c7ebc4898260b25c4adc6b99ec257ce
--- /dev/null
+++ b/irdb-lib/meds2pdb/function_descriptor.h
@@ -0,0 +1,86 @@
+#include <string>
+#include <vector>
+#include <string>
+
+#include <irdb-core>
+#include <irdb-core>
+#include "instruction_descriptor.h"
+
+//class wahoo::Instruction;
+
+using namespace std;
+
+namespace wahoo {
+
+class Function
+{
+  public:
+    Function();
+    Function(IRDB_SDK::VirtualOffset_t);
+    Function(string, IRDB_SDK::VirtualOffset_t, int);
+    ~Function();
+
+    string                    getName() const { return m_name; }
+    void                      setName(const string p_name) { m_name = p_name; }
+    IRDB_SDK::VirtualOffset_t getAddress() const { return m_address; }
+    void                      setAddress(const IRDB_SDK::VirtualOffset_t p_address) { m_address = p_address; }
+    int                       getSize() const { return m_size; }
+    void                      setSize(const int p_size) { m_size = p_size; }
+    int                       getFrameSize() const { return m_frameSize; }
+    void                      setFrameSize(const int p_size) { m_frameSize = p_size; }
+    int                       getFunctionID() const { return m_functionID; }
+    void                      setFunctionID(const int id) { m_functionID = id; }
+
+	
+    bool operator == (const Function &);
+    bool operator == (const IRDB_SDK::VirtualOffset_t);
+    bool operator != (const Function &);
+    bool operator != (const IRDB_SDK::VirtualOffset_t);
+
+    bool isSafe() const { return m_isSafe; }
+    void setSafe() { m_isSafe = true; }
+    void setUnsafe() { m_isSafe = false; }
+
+    void setOutArgsRegionSize(const int p_size) { m_outArgsRegionSize = p_size; }
+    int getOutArgsRegionSize() const { return m_outArgsRegionSize; }
+
+    void setUseFramePointer(const bool p_useFP) { m_useFP = p_useFP; }
+    bool getUseFramePointer() const { return m_useFP; }
+
+    void addInstruction(wahoo::Instruction *);
+    void addStackAllocationInstruction(wahoo::Instruction *);
+    void addStackDeallocationInstruction(wahoo::Instruction *);
+    void addStackReferenceInstruction(wahoo::Instruction *);
+    void addRewriteRule(string p_rule) { m_rewrites.push_back(p_rule); }
+
+    vector<wahoo::Instruction*> getInstructions();
+    vector<wahoo::Instruction*> getStackAllocationInstructions();
+    vector<wahoo::Instruction*> getStackDeallocationInstructions();
+    vector<wahoo::Instruction*> getStackReferencesInstructions();
+
+    vector<string> getRewrites() { return m_rewrites; }
+
+    double getInstructionCoverage();
+    double getInstructionCoverage(int*, int*);
+
+  private:
+    void _init();
+
+    int            m_functionID;
+    string         m_name;
+    IRDB_SDK::VirtualOffset_t    m_address;
+    int            m_size;
+    int            m_frameSize;
+    bool           m_isSafe;
+    bool           m_useFP;
+    int            m_outArgsRegionSize;
+
+    vector<wahoo::Instruction*> m_allInstructions;
+    vector<wahoo::Instruction*> m_stackRefsInstructions;
+    vector<wahoo::Instruction*> m_stackAllocInstructions;
+    vector<wahoo::Instruction*> m_stackDeallocInstructions;
+
+    vector<string>              m_rewrites; // keep track of rewrite rules
+};
+
+}
diff --git a/irdb-lib/meds2pdb/gen_hash.cpp b/irdb-lib/meds2pdb/gen_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..358bc720969e11ff30bdc90e00b9399ac41c655b
--- /dev/null
+++ b/irdb-lib/meds2pdb/gen_hash.cpp
@@ -0,0 +1,240 @@
+/*
+ * gen_hash.c - generic hash table code.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+/*
+ *  gen_hash.c -- generic hashtable implmentation.
+ */
+
+
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <assert.h>
+#include <string.h>
+#include "gen_hash.h"
+#include "spri_alloc.h"
+#include <stdint.h>
+
+#define INITIAL_CAPACITY 128
+
+#define HT_FREE(p,s) (spri_deallocate_type(p,s))
+#define HT_MALLOC(s) (spri_allocate_type(s))
+#define HT_CALLOC(n,s)  (memset((void*)spri_allocate_type((n)*(s)),0,((n)*(s))))
+
+#define TRUE 1
+#define FALSE 0
+
+
+Hashtable *Hashtable_create( long (*hash_func)(void* ), long (*key_compare)(void*, void*))
+{
+    Hashtable *result = (Hashtable*)HT_MALLOC( sizeof(Hashtable) );
+    result->table = (struct entry**)HT_CALLOC( INITIAL_CAPACITY, sizeof(struct entry*) );
+    result->hash_func=hash_func;
+    result->key_compare=key_compare;
+    result->tableLength = INITIAL_CAPACITY;
+
+    result->count = 0;
+    result->threshold = (long)(INITIAL_CAPACITY * 3 / 4);	/* integer calcs for 3/4ths full */
+
+    return result;
+}
+
+void Hashtable_destroy( Hashtable **h )
+{
+assert(0);
+#if 0
+    long i;
+    for( i = (*h)->tableLength - 1; i >= 0; i-- )
+    {
+        struct entry *e = (*h)->table[i];
+        while( e != NULL )
+        {
+            struct entry *deleteEntry = e;
+            e = e->next;
+            HT_FREE( deleteEntry, sizeof(struct entry*) );
+        }
+    }
+    HT_FREE( (*h)->table, h->tableLength*sizeof(struct entry*) );
+    HT_FREE( *h, sizeof(Hashtable) );
+    *h = NULL;
+#endif
+}
+
+void Hashtable_rehash( Hashtable *h )
+{
+    long i;
+    struct entry **oldTable = h->table;
+    long newCapacity = h->tableLength * 2;
+    struct entry **newTable = (struct entry**)HT_CALLOC( newCapacity, sizeof(struct entry*) );
+
+    h->threshold = (long)(newCapacity * 3 / 4); /* integer calcs for 3/4ths full */
+
+    for( i = h->tableLength - 1; i >= 0; i-- )
+    {
+        struct entry *old;
+        for( old = oldTable[i]; old != NULL; )
+        {
+            struct entry *e = old;
+            long index = h->hash_func(e->key) & (newCapacity - 1) ;
+            old = old->next;
+
+            e->next = newTable[index];
+            newTable[index] = e;
+        }
+    }
+
+    HT_FREE( h->table, h->tableLength*sizeof(struct entry*) );
+    h->table = newTable;
+    h->tableLength = newCapacity;
+}
+
+void Hashtable_put( Hashtable *h, void *key, void *value )
+{
+    struct entry *e;
+    // long hash = (long)key;
+    long index = h->hash_func(key) & (h->tableLength-1);
+
+    // make sure the key isn't already present
+    for( e = h->table[index]; e != NULL; e = e->next )
+    {
+        if( h->key_compare(e->key , key ))
+        {
+            e->value = value;
+            return;
+        }
+    }
+
+    if( h->count >= h->threshold )
+    {
+        Hashtable_rehash( h );
+        Hashtable_put( h, key, value );
+    }
+    else
+    {
+        e = (struct entry *)HT_MALLOC( sizeof(struct entry) );
+        e->key = key;
+        e->value = value;
+        e->next = h->table[index];
+        h->table[index] = e;
+        h->count++;
+    }
+}
+
+void *Hashtable_get( const Hashtable *h, void *key )
+{
+    struct entry *e;
+    long index = h->hash_func(key) & (h->tableLength-1);
+
+    for( e = h->table[index]; e != NULL; e = e->next )
+    {
+        if( h->key_compare(e->key , key ))
+            return e->value;
+    }
+    return NULL;
+}
+
+long Hashtable_size( const Hashtable *h )
+{
+    return h->count;
+}
+
+
+
+int Hashtable_containsKey( const Hashtable *h, void *key )
+{
+    return Hashtable_get( h, key ) == NULL ? FALSE : TRUE;
+}
+
+/*
+ * Initialize iterator
+ */
+Hashtable_iterator Hashtable_setup_iterator( Hashtable *h )
+{
+  Hashtable_iterator i;
+  i.ht = h;
+  i.idx = -1;
+  i.current = NULL;
+  return i;
+}
+
+/*
+*  Returns next entry in hash table
+*/
+struct entry* Hashtable_get_next(Hashtable_iterator &iterator)
+{
+    if (!iterator.ht)
+    {
+        fprintf(stderr,"Hashtable_get_next: cannot find the hash table\n");
+        return NULL;
+    }
+    else if (iterator.ht->count <= 0)
+    {
+      fprintf(stderr,"Hashtable_get_next: the hashtable count is <= 0   0x%p\n", (void*)iterator.ht);
+      return NULL;
+    }
+
+    if (iterator.idx < 0)
+    {
+      int i=0;
+      // first time, find the first real entry
+      for (i = 0; i < iterator.ht->tableLength; ++i)
+      {
+        if (iterator.ht->table[i] != NULL)
+        {
+          iterator.idx = i;
+          iterator.current = iterator.ht->table[i];
+          return iterator.current;
+        }
+      }
+      fprintf(stderr,"Hashtable_get_next: no keys found in hash table\n");
+      return NULL; // empty table, no keys found
+    }
+    else
+    {
+        if (iterator.current)
+        { 
+            if (iterator.current->next)
+            {
+                iterator.current = iterator.current->next;
+                return iterator.current;
+            }
+            else
+            {
+                int i=0;
+                // get the next entry
+                for (i = iterator.idx + 1; i < iterator.ht->tableLength; ++i)
+                {
+                    if (iterator.ht->table[i] != NULL)
+                    {
+                        iterator.idx = i;
+                        iterator.current = iterator.ht->table[i];
+                        return iterator.current;
+                    }
+                }
+                return NULL; // we're done
+            }
+        }
+        return NULL; // empty table, no keys found
+    } 
+} 
+
diff --git a/irdb-lib/meds2pdb/gen_hash.h b/irdb-lib/meds2pdb/gen_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..eb8670042b50f3944ab51420117ed4cd9774011a
--- /dev/null
+++ b/irdb-lib/meds2pdb/gen_hash.h
@@ -0,0 +1,99 @@
+/*
+ * gen_hash.h - generic hash table code.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+
+// Hashtable.h
+
+#ifndef HASHTABLE_H
+#define HASHTABLE_H
+
+
+// opaque structure
+typedef struct gen_hashtable Hashtable;
+
+struct entry
+{
+    void *key;
+    void *value;
+    struct entry *next;
+};
+
+struct gen_hashtable
+{
+    struct entry **table;
+    long tableLength;
+    long count;
+    long threshold;
+    long (*hash_func)(void*);
+    long (*key_compare)(void*, void*);
+};
+
+struct gen_hashtable_iterator
+{
+    Hashtable*     ht;
+    long           idx;
+    struct entry*  current;
+};
+
+typedef struct gen_hashtable_iterator Hashtable_iterator;
+
+/**
+ * Creates an empty hashtable.
+ */
+Hashtable *Hashtable_create(long (*hash)(void*), long (*key_compare)(void*,void*));
+
+/**
+ * Free the hashtable memory.
+ */
+void Hashtable_destroy( Hashtable **h );
+
+/**
+ * Puts the key, value pair into the hashtable.
+ */
+void Hashtable_put( Hashtable *h, void *key, void *value );
+
+/**
+ * Returns the value associated with the key.
+ */
+void *Hashtable_get( const Hashtable *h, void *key );
+
+/**
+ * Returns the number of values in the hashtable.
+ */
+long Hashtable_size( const Hashtable *h );
+
+
+/**
+ * Returns TRUE if the hashtable contains the specified key.
+ */
+int Hashtable_containsKey( const Hashtable *h, void *key );
+
+/**
+ * Hash table iterator
+ */
+
+Hashtable_iterator Hashtable_setup_iterator( Hashtable *h );
+struct entry* Hashtable_get_next(Hashtable_iterator &i);
+
+#endif
+
diff --git a/irdb-lib/meds2pdb/instrmap_hash.cpp b/irdb-lib/meds2pdb/instrmap_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3a9bc6c062986d8c4278f5c3fd6cd34534c76e8b
--- /dev/null
+++ b/irdb-lib/meds2pdb/instrmap_hash.cpp
@@ -0,0 +1,43 @@
+/*
+ * instrmap_hash.c - hash table for instrumentation details.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include "instrmap_hash.h"
+
+Hashtable *instrmaps_hash=NULL;
+
+long instrmaps_compute_hash(void* key1)
+{
+        instrmap_hash_key_t * a_key=(instrmap_hash_key_t *)key1;
+
+        return a_key->pc;
+}
+
+long instrmaps_key_compare(void* key1, void* key2)
+{
+        instrmap_hash_key_t * a_key=(instrmap_hash_key_t *)key1;
+        instrmap_hash_key_t * b_key=(instrmap_hash_key_t *)key2;
+
+        return a_key->pc == b_key->pc;
+}
+
+
diff --git a/irdb-lib/meds2pdb/instrmap_hash.h b/irdb-lib/meds2pdb/instrmap_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..1b6239596186a4c99fb3c9a99e39f25c8b0738c0
--- /dev/null
+++ b/irdb-lib/meds2pdb/instrmap_hash.h
@@ -0,0 +1,49 @@
+/*
+ * instrmap_hash.h - hash table for instrumentation details.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef instrmap_hash_h
+#define instrmap_hash_h
+
+#include "meds_all.h"
+
+
+extern Hashtable *instrmaps_hash;
+struct instrmap_hash_key
+{
+        int pc;
+};
+typedef struct instrmap_hash_key instrmap_hash_key_t;
+
+struct instrmap_hash_value
+{
+	int func_addr;
+	int site_alloc;
+        int size;
+};
+typedef struct instrmap_hash_value instrmap_hash_value_t;
+
+long instrmaps_compute_hash(void* key1);
+
+long instrmaps_key_compare(void* key1, void* key2);
+
+#endif
diff --git a/irdb-lib/meds2pdb/instruction_descriptor.cpp b/irdb-lib/meds2pdb/instruction_descriptor.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d01255f9196ab43ce70ecae5a651bb6bedece10e
--- /dev/null
+++ b/irdb-lib/meds2pdb/instruction_descriptor.cpp
@@ -0,0 +1,86 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include "instruction_descriptor.h"
+#include "function_descriptor.h"
+
+using namespace IRDB_SDK;
+
+wahoo::Instruction::Instruction()
+{
+  m_address = 0;
+  m_size = -1;
+  m_function = NULL;
+  m_asm = "";
+
+  m_allocSite = false;
+  m_deallocSite = false;
+  m_stackRef = false;
+  m_varStackRef = false;
+  m_isVisited = false;
+  m_data = NULL;
+}
+
+wahoo::Instruction::Instruction(VirtualOffset_t  p_address, int p_size, Function* p_func)
+{
+  m_address = p_address;
+  m_size = p_size;
+  m_function = p_func;
+  m_isVisited = false;
+
+  m_allocSite = false;
+  m_deallocSite = false;
+  m_stackRef = false;
+  m_data = NULL;
+}
+
+wahoo::Instruction::~Instruction()
+{
+  m_function = NULL;
+}
+
+// warning: MEDS annotation (via IDA Pro plugin) is not perfect
+//          and may miss fumctions
+void wahoo::Instruction::markAllocSite() 
+{ 
+  m_allocSite = true; 
+  if (m_function)
+    m_function->addStackAllocationInstruction(this);
+}
+
+void wahoo::Instruction::markDeallocSite() 
+{ 
+  m_deallocSite = true; 
+  if (m_function)
+    m_function->addStackDeallocationInstruction(this);
+}
+
+void wahoo::Instruction::markStackRef() 
+{ 
+  m_stackRef = true; 
+  if (m_function)
+    m_function->addStackReferenceInstruction(this);
+}
+
+void wahoo::Instruction::markVarStackRef() 
+{ 
+  m_varStackRef = true; 
+}
+
diff --git a/irdb-lib/meds2pdb/instruction_descriptor.h b/irdb-lib/meds2pdb/instruction_descriptor.h
new file mode 100644
index 0000000000000000000000000000000000000000..2cb5bfd2ec7d8dece2253460aee4e4df8f7ba761
--- /dev/null
+++ b/irdb-lib/meds2pdb/instruction_descriptor.h
@@ -0,0 +1,68 @@
+#ifndef _instruction_h_
+#define _instruction_h_
+
+#include <string>
+#include <set>
+#include <irdb-core>
+
+#include <irdb-core>
+
+using namespace std;
+
+
+namespace wahoo {
+
+class Function;
+
+
+class Instruction {
+  public:
+    Instruction();
+    Instruction(IRDB_SDK::VirtualOffset_t, int p_size = -1, Function* = NULL);
+    ~Instruction();
+
+    void setSize(int p_size) { m_size = p_size; }
+    void setFunction(Function *p_func) { m_function = p_func; }
+
+    void markAllocSite();
+    void markDeallocSite();
+    void markStackRef();
+    void markVarStackRef();
+
+    IRDB_SDK::VirtualOffset_t     getAddress() const { return m_address; }
+    int             getSize() const { return m_size; }
+    Function*       getFunction() const { return m_function; }
+    string          getAsm() const { return m_asm; }
+    void            setAsm(string p_str) { m_asm = p_str; }
+    void            setData(void *dataPtr, int len);
+    unsigned char*  getData() const { return m_data; }
+    void            setData(void *data) { m_data = (unsigned char*) data; }
+
+    bool isStackRef() const { return m_stackRef; }
+    bool isVarStackRef() const { return m_varStackRef; }
+    bool isAllocSite() const { return m_allocSite; }
+    bool isDeallocSite() const { return m_deallocSite; }
+
+    // keep track of whether instruction has been visited during execution
+    void setVisited() { m_isVisited = true; }
+    bool isVisited() const { return m_isVisited; }
+
+  private:
+    IRDB_SDK::VirtualOffset_t     m_address;
+    int             m_size;
+    Function*       m_function;
+    string          m_asm;
+    unsigned char*  m_data;
+
+    bool            m_allocSite;
+    bool            m_deallocSite;
+    bool            m_stackRef;
+    bool            m_varStackRef;
+
+    bool            m_isVisited;
+
+};
+
+}
+
+#endif
diff --git a/irdb-lib/meds2pdb/instrument.h b/irdb-lib/meds2pdb/instrument.h
new file mode 100644
index 0000000000000000000000000000000000000000..80f85f760bbcfb1a967dd9bb1e1f28b6a908e296
--- /dev/null
+++ b/irdb-lib/meds2pdb/instrument.h
@@ -0,0 +1,68 @@
+/*
+ * instrument.h -- see instrument.c
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+/*
+ * instrument.h -- see instrument.c
+ * author - jdh8d
+ */
+#ifndef _instrument_h
+#define _instrument_h
+
+
+/*
+no needed for SPRI
+void add_smp_instrumentation(strata_fragment_t *frag, VirtualOffset_t PC, insn_t *insn);
+void add_smp_postinstrumentation(strata_fragment_t *frag, VirtualOffset_t PC, insn_t *insn);
+*/
+
+
+
+
+
+
+/*  the registers are pushed onto the stack with "push eax; lahf, pusha" in this order */
+typedef struct reg_values reg_values_t;
+struct reg_values 
+{
+       	int edi;
+       	int esi;
+       	int ebp;
+       	int esp_dummy;
+       	int ebx;
+       	int edx;
+       	int ecx;
+       	int eax;
+       	int eflags;
+};
+
+
+/*
+no needed for SPRI
+VirtualOffset_t targ_watched_called_instrument(VirtualOffset_t next_PC, watch *w, strata_fragment_t *frag);
+*/
+
+
+/* #define NO_ANNOT_STACK */
+
+#endif
+
diff --git a/irdb-lib/meds2pdb/meds2pdb.cpp b/irdb-lib/meds2pdb/meds2pdb.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..67539ea7bb64632efcce1d1181cb76e190bc4ed7
--- /dev/null
+++ b/irdb-lib/meds2pdb/meds2pdb.cpp
@@ -0,0 +1,502 @@
+/*
+ * Copyright (c) 2014 - Zephyr Software LLC
+ *
+ * This file may be used and modified for non-commercial purposes as long as
+ * all copyright, permission, and nonwarranty notices are preserved.
+ * Redistribution is prohibited without prior written consent from Zephyr
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <iostream>
+#include <iomanip>
+#include <fstream>
+#include <map>
+#include <time.h>
+#include <string.h>
+#include "rewriter.h"
+#include <pqxx/pqxx>
+#include <stdlib.h>
+#include "MEDS_AnnotationParser.hpp"
+#include "MEDS_FuncPrototypeAnnotation.hpp"
+#include <irdb-core>
+
+using namespace std;
+using namespace pqxx;
+using namespace IRDB_SDK;
+using namespace MEDS_Annotation;
+
+#include <sstream>
+
+string functionTable;
+string addressTable;
+string instructionTable;
+string typesTable;
+string icfsTable;
+string icfsMapTable;
+
+static const int STRIDE = 50;
+
+template <class T>
+inline std::string my_to_string (const T& t)
+{
+        std::stringstream ss;
+        ss << t;
+        return ss.str();
+}
+
+
+int next_address_id=0;
+
+map<VirtualOffset_t,int> address_to_instructionid_map;
+map<wahoo::Instruction*,int> instruction_to_addressid_map;
+
+// extract the file id from the md5 hash and the program name
+int get_file_id(char *progName, char *md5hash)
+{
+  connection conn;
+  work txn(conn);
+  txn.exec("SET client_encoding='LATIN1';");
+
+  string query = "SELECT file_id FROM file_info WHERE hash=";
+  query += txn.quote(string(md5hash));
+  query += " AND url LIKE";
+	/* the plus 7 here is to drop "psprog_" from the name */
+  query += txn.quote(string("%") + string(progName+7) + string("%"));
+
+  result r = txn.exec(query);
+
+  for (result::const_iterator row = r.begin(); row != r.end(); ++row)
+  {
+    return row["file_id"].as<int>();
+  }
+  
+  return -1; // error
+}
+
+
+// insert addresses & instructions into DB
+void insert_instructions(int fileID, const vector<wahoo::Instruction*> &instructions, const vector<wahoo::Function*> &functions)
+{
+	cerr << "Inserting instructions in the DB"<<endl;
+	connection conn;
+	work txn(conn);
+	// for each instruction:
+	//    get address, insert into address table
+	// for each instruction:
+	//    populate instruction table
+
+	assert(getenv("SELF_VALIDATE")==nullptr || instructions.size() > 0 );
+
+	pqxx::tablewriter W_addrs(txn,addressTable);
+	for (auto i = 0U; i < instructions.size(); i ++ )
+	{
+    		char buf[128];
+
+		wahoo::Instruction *instruction = instructions[i];
+		auto   addr = instruction->getAddress();
+
+		// assign an instruction id
+		address_to_instructionid_map[addr]=next_address_id++;
+
+		// assign an address id
+		int address_id = next_address_id++;
+		instruction_to_addressid_map[instruction]=address_id;
+
+		snprintf(buf,sizeof(buf),"%lld", (long long)addr);
+
+
+		// insert into address table
+		vector<string> row=
+			{  
+				to_string(address_id),
+				to_string(fileID),
+				string(buf),
+				"-1"
+			}; 
+		W_addrs << row;
+
+	}
+	W_addrs.complete();
+
+	pqxx::tablewriter W_insns(txn,instructionTable);
+  	for (auto i = 0U; i < instructions.size(); i ++)
+	{
+		const auto instruction = instructions[i];
+		const auto addr = instruction->getAddress();
+		const auto instruction_id=address_to_instructionid_map[addr];
+		const auto address_id=instruction_to_addressid_map[instruction];
+      		const auto parent_function_id = instruction->getFunction() ?  instruction->getFunction()->getFunctionID() : -1 ;
+		const auto orig_address_id=address_id;
+		const auto fallthrough_address_id="-1";
+		const auto target_address_id="-1";
+		const auto icfs_id="-1";
+		const auto ehpgm_id="-1";
+		const auto ehcss_id="-1";
+
+      		const auto data = (unsigned char*) instruction->getData();
+		ostringstream hex_data;
+		hex_data << setfill('0') << hex;;
+		for (auto i = 0; i < instruction->getSize(); ++i)
+			hex_data << setw(2) << (int)(data[i]&0xff);
+
+		const auto & encoded_data=hex_data.str();
+		const auto callback=string("");
+      		const auto & comment = instruction->getAsm();
+		const auto ind_target_address_id="-1";
+		const auto doip_id="-1";
+
+		const auto row=vector<string>(
+			{  
+				to_string(instruction_id),
+				to_string(address_id),
+				to_string(parent_function_id),
+				to_string(orig_address_id),
+				fallthrough_address_id,
+				target_address_id,
+				icfs_id,
+				ehpgm_id,
+				ehcss_id,
+				encoded_data,
+				callback,
+				comment,
+				ind_target_address_id,
+				doip_id
+			}) ; 
+		W_insns << row;
+
+
+
+	};
+	W_insns.complete();
+
+  txn.commit();
+  cerr << "Done inserting instructions in the DB"<<endl;
+}
+
+void insert_functions(int fileID, const vector<wahoo::Function*> &functions  )
+{
+  connection conn;
+  work txn(conn);
+  txn.exec("SET client_encoding='LATIN1';");
+
+  assert(getenv("SELF_VALIDATE")==nullptr || functions.size() > 0 );
+
+  // bulk insert of function information into the DB
+  for (auto i = 0U; i < functions.size(); i += STRIDE)
+  {  
+    string query = "INSERT INTO " + functionTable;
+    query += " (function_id, name, stack_frame_size, out_args_region_size, use_frame_pointer, is_safe) VALUES ";
+
+
+    for (auto j = i; j < i + STRIDE; ++j)
+    {
+      if (j >= functions.size()) break;
+      wahoo::Function *f = functions[j];
+      string functionName = f->getName();
+      int functionFrameSize =  f->getFrameSize(); 
+
+      int function_id = j;
+      f->setFunctionID(function_id);
+
+      int outArgsRegionSize = f->getOutArgsRegionSize();
+      bool useFP = f->getUseFramePointer();
+      bool isSafe = f->isSafe();
+
+      if (j != i) query += ",";
+      query += "(";
+      query += txn.quote(function_id) + ",";
+      query += txn.quote(functionName) + ",";
+      query += txn.quote(functionFrameSize) + ",";
+      query += txn.quote(outArgsRegionSize) + ",";
+      query += txn.quote(useFP) + ",";
+      query += txn.quote(isSafe) + ")";
+
+    }
+
+    txn.exec(query);
+  }
+
+  txn.commit(); // must commit o/w everything will be rolled back
+}
+
+void update_functions(int fileID, const vector<wahoo::Function*> &functions  )
+{
+  connection conn;
+  work txn(conn);
+  txn.exec("SET client_encoding='LATIN1';");
+
+  assert(getenv("SELF_VALIDATE")==nullptr || functions.size() > 0 );
+
+  // bulk insert of function information into the DB
+  string query;
+  for (auto i = 0U; i < functions.size(); i += STRIDE )
+  {  
+    query="";
+    for (auto j = i; j < i + STRIDE; ++j)
+    {
+        if (j >= functions.size()) break;
+      	wahoo::Function *f = functions[j];
+      	string functionName = f->getName();
+	auto functionAddress = f->getAddress();
+      	//int functionSize = f->getSize();
+      	int function_id = f->getFunctionID();
+      	//int outArgsRegionSize = f->getOutArgsRegionSize();
+      	//bool useFP = f->getUseFramePointer();
+	int insnid=-1; 	// NOT_IN_DATABASE
+
+
+	// if a function has a valid address, but the address isn't in the table...
+	if(functionAddress!=0 && 
+		address_to_instructionid_map.find(functionAddress)==address_to_instructionid_map.end())
+	{
+abort();
+		// remove the function from the list of valid functions.
+		query+="delete from "+functionTable;
+		query+=" where function_id = " + txn.quote(my_to_string(function_id));
+		query += ";";
+		
+	}
+	else
+	{
+		if(functionAddress!=0)	
+			insnid=address_to_instructionid_map[functionAddress];
+    		query += "update " + functionTable;
+		query += " set entry_point_id = " + txn.quote(my_to_string(insnid));
+    		query += " where function_id = " + txn.quote(my_to_string(function_id));
+		query += ";";
+	}
+
+    }
+    txn.exec(query);
+  }
+
+  txn.commit(); // must commit o/w everything will be rolled back
+}
+
+/*
+	typedef enum IRDB_Type {
+		T_UNKNOWN = 0, T_NUMERIC = 1, T_POINTER = 2, 
+		T_INT = 10, T_CHAR = 11, T_FLOAT = 12, T_DOUBLE = 13,
+		T_VARIADIC = 20, T_TYPEDEF = 21, T_SUBTYPE = 22, 
+		T_FUNC = 100, T_AGGREGATE = 101
+	} IRDB_Type;
+
+// MUST MATCH typedef in type.hpp in libIRDB-core!!!
+*/
+
+static int getNewTypeId()
+{
+	// start at 5000 so we don't clash with predefined type ids
+	static int next_type_id=5000; 
+	return next_type_id++;
+}
+
+void populate_predefined_types()
+{
+	connection conn;
+	work txn(conn);
+	string q = "SET client_encoding='LATIN1';";
+	q += "INSERT into " + typesTable + " (type_id, type, name, ref_type_id, ref_type_id2) values ('0', '0','unknown','-1','-1');";
+	q += "INSERT into " + typesTable + " (type_id, type, name, ref_type_id, ref_type_id2) values ('1', '1','numeric','-1','-1');";
+	q += "INSERT into " + typesTable + " (type_id, type, name, ref_type_id, ref_type_id2) values ('2', '2','pointer','0','-1');";
+	txn.exec(q);
+	txn.commit(); 
+}
+
+void update_function_prototype(const vector<wahoo::Function*> &functions, char* annotFile)
+{
+	populate_predefined_types();
+
+	MEDS_Annotations_t annotations;
+
+	ifstream annotationif(annotFile, ifstream::in);
+	if (annotationif.is_open())
+	{
+		MEDS_AnnotationParser annotationParser(annotationif);
+		annotations = annotationParser.getAnnotations();
+	}
+	else
+	{
+		cerr << "warning: cannot open: " << annotFile << endl;
+	}
+
+	cerr << "annotations size: " << annotations.size() << endl;
+	cerr << "functions size: " << functions.size() << endl;
+
+	connection conn;
+	work txn(conn);
+	txn.exec("SET client_encoding='LATIN1';");
+
+	for (auto i = 0U; i < functions.size(); i += STRIDE)
+	{  
+		string q = "";
+		for (auto j = i; j < i + STRIDE; ++j)
+		{
+			if (j >= functions.size()) break;
+			wahoo::Function *f = functions[j];
+      			int function_id = f->getFunctionID();
+			auto functionAddress = f->getAddress();
+			VirtualOffset vo(functionAddress);
+
+			//MEDS_FuncPrototypeAnnotation* fn_prototype_annot = NULL; 
+			//MEDS_FuncPrototypeAnnotation* fn_returntotype_annot = NULL; 
+			
+			std::vector<MEDS_Arg> *args = NULL;
+			MEDS_Arg *returnArg = NULL;
+
+			if (annotations.count(vo) > 0)
+			{
+				std::pair<MEDS_Annotations_t::iterator,MEDS_Annotations_t::iterator> ret; 
+				ret = annotations.equal_range(vo);
+				MEDS_FuncPrototypeAnnotation* p_annotation; 
+				for ( auto it = ret.first; it != ret.second; ++it)
+				{    
+					MEDS_AnnotationBase *base_type=(it->second);
+					p_annotation = dynamic_cast<MEDS_FuncPrototypeAnnotation*>(base_type);
+					if(p_annotation == NULL || !p_annotation->isValid()) 
+						continue;
+
+					if (p_annotation->getArgs())
+						args = p_annotation->getArgs();
+
+					if (p_annotation->getReturnArg())
+						returnArg = p_annotation->getReturnArg();
+				}    
+			}
+
+			// we should have 2 valid annotations per function
+			// one for the args, one for the return type
+			if (args)
+			{
+				// (1) define new aggregate type
+				// (2) define new return type
+				// (3) define new function type (combo (1) + (2))
+				int aggregate_type_id = getNewTypeId();
+				int func_type_id = getNewTypeId();
+				int basic_type_id = IRDB_SDK::itUnknown;
+
+				for (auto i = 0U; i < args->size(); ++i)
+				{
+					if ((*args)[i].isNumericType())
+						basic_type_id = itNumeric;
+					else if ((*args)[i].isPointerType())
+						basic_type_id = itPointer;
+
+					q += "INSERT into " + typesTable + " (type_id, type, name, ref_type_id, pos) VALUES (";
+					q += txn.quote(my_to_string(aggregate_type_id)) + ",";
+					q += txn.quote(my_to_string(itAggregate)) + ",";
+
+					q += txn.quote(string(f->getName()) + "_arg") + ",";
+					q += txn.quote(my_to_string(basic_type_id)) + ",";
+					q += txn.quote(my_to_string(i)) + ");";
+				}
+
+				int return_type_id = itUnknown;
+				if (returnArg) 
+				{
+					if (returnArg->isNumericType())
+						return_type_id = itNumeric;
+					else if (returnArg->isPointerType())
+						return_type_id = itPointer;
+					else
+						return_type_id = itUnknown;
+				}
+
+				// new function type id (ok to have duplicate prototypes)
+				// ref_type_id is the return type id
+				// ref_type_id2 is the type id for the aggregated type 
+				//     that describes the function arguments
+				q += "INSERT into " + typesTable + " (type_id, type, name, ref_type_id, ref_type_id2) VALUES (";
+
+				q += txn.quote(my_to_string(func_type_id)) + ",";
+				q += txn.quote(my_to_string(itFunc)) + ",";
+				q += txn.quote(string(f->getName()) + "_func") + ",";
+				q += txn.quote(my_to_string(return_type_id)) + ",";
+				q += txn.quote(my_to_string(aggregate_type_id)) + ");";
+
+				// update the type id in the function table
+				q += "UPDATE " + functionTable;
+				q += " SET type_id = " + txn.quote(my_to_string(func_type_id));
+				q += " where function_id = " + txn.quote(my_to_string(function_id)) + "; ";
+			} // update function prototype
+		} // strided
+
+		if (q.size() > 0)
+			txn.exec(q);
+	} // outer loop
+
+ 	txn.commit(); // must commit o/w everything will be rolled back
+}
+
+int main(int argc, char **argv)
+{
+  	if (argc != 11)
+  	{
+    		cerr << "usage: " << argv[0] << " <annotations file> <info annotation file> <file id> <func tab name> <insn tab name> <addr tab name> <types tab name> <icfs table name> <icfs map table name> <elf file>" << endl;
+    		return 1;
+  	}
+
+  	char *annotFile = argv[1];
+  	char *infoAnnotFile = argv[2];
+  	char *fid=argv[3];
+  	char *myFunctionTable=argv[4];
+  	char *myInstructionTable=argv[5];
+  	char *myAddressTable=argv[6];
+  	char *myTypesTable=argv[7];
+  	char *myicfsTable=argv[8];
+  	char *myicfsMapTable=argv[9];
+  	char *elfFile=argv[10];
+
+	cout<<"Annotation file: "<< annotFile<<endl;
+	cout<<"Info annotation file: "<< infoAnnotFile<<endl;
+	cout<<"File ID: "<< fid<<endl;
+	cout<<"FTN: "<< myFunctionTable<<endl;
+	cout<<"ITN: "<< myInstructionTable<<endl;
+	cout<<"ATN: "<< myAddressTable<<endl;
+	cout<<"TYP: "<< myTypesTable<<endl;
+	cout<<"ICFSTab: "<< myicfsTable<<endl;
+	cout<<"ICFSMapTab: "<< myicfsMapTable<<endl;
+	cout<<"elfFile: "<< elfFile<<endl;
+
+	// set global vars for importing.
+	functionTable=myFunctionTable;
+	addressTable=myAddressTable;
+	instructionTable=myInstructionTable;
+	typesTable=myTypesTable;
+	icfsTable=myicfsTable;
+	icfsMapTable=myicfsMapTable;
+
+  	Rewriter *rewriter = new Rewriter(elfFile, annotFile);
+
+  	int fileID = atoi(fid);
+	if(fileID<=0)
+	{
+		cerr << "Bad fileID: " << fid <<endl;
+		exit(1);
+	}
+
+  	// get functions & instructions from MEDS
+  	vector<wahoo::Function*> functions = rewriter->getAllFunctions();
+  	vector<wahoo::Instruction*> instructions = rewriter->getAllInstructions();
+
+  	cerr << "Number of functions: " << functions.size() << endl;
+  	cerr << "Number of instructions: " << instructions.size() << endl;
+  	insert_functions(fileID, functions);
+  	insert_instructions(fileID, instructions, functions);
+  	update_functions(fileID, functions);
+
+	// add function prototype information to the IRDB
+	update_function_prototype(functions, infoAnnotFile);
+	exit(0);
+}
diff --git a/irdb-lib/meds2pdb/meds_all.h b/irdb-lib/meds2pdb/meds_all.h
new file mode 100644
index 0000000000000000000000000000000000000000..f551ac1dc631a6bd446d07de7c1fb21b087f8454
--- /dev/null
+++ b/irdb-lib/meds2pdb/meds_all.h
@@ -0,0 +1,54 @@
+/*
+ * meds_all.h
+ *
+ * Copyright (c) 2011 - University of Virginia 
+ *
+ * This file is part of the STROBE (STack Rewriting of Binary Executables) project.
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef _MEDS_ANNOT_H
+#define _MEDS_ANNOT_H
+
+#include <stdio.h>
+#include <string.h>
+#include <assert.h>
+
+#include <irdb-core>
+
+using namespace IRDB_SDK;
+
+#include "strata_defines.h"
+
+/* x86_32-specific headers */
+#include "instrument.h"
+
+#include "spri_alloc.h"
+#include "bitvector.h"
+#include "gen_hash.h"
+#include "constant_hash.h"
+#include "stackref_hash.h"
+#include "framesize_hash.h"
+#include "framerestore_hash.h"
+#include "instrmap_hash.h"
+#include "funclist_hash.h"
+#include "constant_hash.h"
+
+#include <inttypes.h>
+
+#endif
diff --git a/irdb-lib/meds2pdb/null_transform.cpp b/irdb-lib/meds2pdb/null_transform.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..c675d20ce826ae346d1a3faa35ce524f010faec9
--- /dev/null
+++ b/irdb-lib/meds2pdb/null_transform.cpp
@@ -0,0 +1,120 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <iostream>
+
+#include <irdb-core>
+
+// #include "elfio/elfio.hpp"
+
+#include "null_transform.h"
+#include "stackref_hash.h"
+
+
+
+using namespace wahoo;
+
+//
+// The NullTransform produces assembly SPRI rules that
+// are semantically equivalent to the original instructions.
+// 
+// The following instructions are currently transformed:
+//
+//    leave
+//    ret
+//    sub esp, K     # when the instruction is used to allocate the stack frame 
+//    push ebp
+//    pop ebp
+//
+// This trasformation is used primarily for testing purposes.
+// 
+
+void NullTransform::rewrite()
+{
+  // only transform instructions contained in well-defined functions
+  for (map<VirtualOffset_t, wahoo::Function*>::iterator it = m_functions.begin(); it != m_functions.end(); ++it)
+  {
+	  VirtualOffset_t addr = it->first;
+    wahoo::Function* f = it->second;
+    if (!f)
+    {
+      fprintf(stderr,"nulltransform: warning: NULL function data structure at pc: 0x%8p\n", (void*)addr);
+      continue;
+    }
+
+    for (auto j = 0U; j < f->getInstructions().size(); ++j)
+    {
+      wahoo::Instruction *instr = f->getInstructions()[j];
+      char buf[1024];
+      sprintf(buf, "%s", instr->getAsm().c_str());
+      fprintf(getAsmSpri(), "# orig: %s\n", buf);
+      if (strstr(buf,"leave"))
+      {
+        fprintf(getAsmSpri(), "0x%8p -> .\n", (void*)instr->getAddress());
+        fprintf(getAsmSpri(), ". ** leave\n");
+        fprintf(getAsmSpri(), ". -> 0x%8p\n", (void*)(instr->getAddress() + instr->getSize()));
+      }
+      else if (strstr(buf,"ret"))
+      {
+        fprintf(getAsmSpri(), "0x%8p -> .\n", (void*)instr->getAddress());
+        fprintf(getAsmSpri(), ". ** nop\n");
+        fprintf(getAsmSpri(), ". ** ret\n");
+        fprintf(getAsmSpri(), ". -> 0x%8p\n", (void*)(instr->getAddress() + instr->getSize()));
+      }
+      else if (instr->isAllocSite())
+      {
+        unsigned int allocSize;
+        sscanf(buf,"sub esp , %x", &allocSize);
+        fprintf(getAsmSpri(), "# alloc site: stack frame size: %u\n", allocSize);
+        if (strstr(buf,"sub esp"))
+        {
+          fprintf(getAsmSpri(), "0x%8p -> .\n", (void*)instr->getAddress());
+          fprintf(getAsmSpri(), ". ** nop\n");
+          fprintf(getAsmSpri(), ". ** sub esp, 0x%x\n", allocSize + 283);
+          fprintf(getAsmSpri(), ". ** add esp, 0x%x\n", 283);
+          fprintf(getAsmSpri(), ". -> 0x%8p\n", (void*)(instr->getAddress() + instr->getSize()));
+        }
+      }
+      else if (strstr(buf,"push ebp"))
+      {
+        fprintf(getAsmSpri(), "0x%8p -> .\n", (void*)(instr->getAddress()));
+        fprintf(getAsmSpri(), ". ** push ebp\n");
+        fprintf(getAsmSpri(), ". ** nop\n");
+        fprintf(getAsmSpri(), ". ** add ebp, 1\n");
+        fprintf(getAsmSpri(), ". ** sub ebp, 1\n");
+        fprintf(getAsmSpri(), ". ** push ebp\n");
+        fprintf(getAsmSpri(), ". ** pop ebp\n");
+        fprintf(getAsmSpri(), ". -> 0x%8p\n", (void*)(instr->getAddress() + instr->getSize()));
+      }
+      else if (strstr(buf,"pop ebp"))
+      {
+        fprintf(getAsmSpri(), "0x%8p -> .\n", (void*)instr->getAddress());
+        fprintf(getAsmSpri(), ". ** push ebp\n");
+        fprintf(getAsmSpri(), ". ** pop ebp\n");
+        fprintf(getAsmSpri(), ". ** nop\n");
+        fprintf(getAsmSpri(), ". ** add ebp, 1\n");
+        fprintf(getAsmSpri(), ". ** sub ebp, 1\n");
+        fprintf(getAsmSpri(), ". ** pop ebp\n");
+        fprintf(getAsmSpri(), ". ** nop\n");
+        fprintf(getAsmSpri(), ". -> 0x%8p\n", (void*)(instr->getAddress() + instr->getSize()));
+      }
+    }
+  }
+}
diff --git a/irdb-lib/meds2pdb/null_transform.h b/irdb-lib/meds2pdb/null_transform.h
new file mode 100644
index 0000000000000000000000000000000000000000..7265ea9c5a0a80183941c3c9504c1a2c28f66c27
--- /dev/null
+++ b/irdb-lib/meds2pdb/null_transform.h
@@ -0,0 +1,10 @@
+#include "rewriter.h"
+
+class NullTransform : public Rewriter
+{
+  public:
+    NullTransform(char *p_elf, char *p_annot, char *p_spri) : Rewriter(p_elf, p_annot) {}
+
+  public:
+    void rewrite();
+};
diff --git a/irdb-lib/meds2pdb/read_annot_file.cpp b/irdb-lib/meds2pdb/read_annot_file.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..10508f2376e63d09e0886e3a9c9d18789470994a
--- /dev/null
+++ b/irdb-lib/meds2pdb/read_annot_file.cpp
@@ -0,0 +1,691 @@
+/*
+ * shadow.c - see below.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+// First pass, we'll handle the following annotations:
+//
+// FUNC               - function
+// INSTR              - instruction
+// MEMORYHOLE         - not allowed to write into these
+//
+// DATAREF STACK      - allocate stack
+// DEALLOC STACK      - deallocate stack
+//
+// PTRIMMEDESP        - stack references off ESP
+// PTRIMMEDEBP        - stack references off EBP
+
+// #include <stdio.h>
+// #include <string.h>
+#include "meds_all.h"
+
+template <class T>
+void ignore_result(const T& v) { (void)v; }
+
+/*
+ *  read_annot_file - read the annotations file provided by IDA Pro.
+ */
+void read_annot_file(char fn[])
+{
+	FILE* fin=nullptr;
+	VirtualOffset_t addr=0;
+	union { int size, type;} size_type_u;
+	char type[200];
+	char scope[200];
+	char remainder[200000];
+	/*char * objname; 
+	int pid=0;
+	int var_length=0; 
+	int bitvector_size_bits=0;
+	*/
+	int line=0;
+
+
+	constants_hash=	Hashtable_create(constants_compute_hash, constants_key_compare);
+	stackrefs_hash=	Hashtable_create(stackrefs_compute_hash, stackrefs_key_compare);
+	framerestores_hash=	Hashtable_create(framerestores_compute_hash, framerestores_key_compare);
+	instrmaps_hash=	Hashtable_create(instrmaps_compute_hash, instrmaps_key_compare);
+	funclists_hash=	Hashtable_create(funclists_compute_hash, funclists_key_compare);
+
+	if(fn[0]==0)
+		return;
+
+	fin=fopen(fn, "r");
+
+	if(!fin)
+	{
+		fprintf(stderr,"Cannot open strata annotation file %s\n", fn);
+		return;
+	}
+
+
+
+	do 
+	{
+		unsigned int tmp=0;
+		ignore_result(fscanf(fin, "%x %d\n", &tmp, &size_type_u.size));
+		addr=tmp;
+
+		if(feof(fin))		// deal with blank lines at the EOF
+			break;
+		
+		ignore_result(fscanf(fin, "%s%s", type,scope));
+
+		int annot_type;
+		int is_spec_annot=FALSE;
+		if(size_type_u.type<-255)
+		{
+			annot_type=size_type_u.type+256;
+			size_type_u.type=size_type_u.type+256;
+			is_spec_annot=TRUE;
+		}
+		else
+			annot_type=size_type_u.type;
+
+
+		/* check for speculative annotations */
+//		if(is_spec_annot && strata_opt_do_smp_verify_profile)
+		if(is_spec_annot)
+		{
+			/* skip this annotation */
+			ignore_result(fgets(remainder, sizeof(remainder), fin));
+			line++;
+			continue;
+		}
+
+		/* if the size > 0, then this is a declaration of a variable */
+		if(strcmp(type,"FUNC")==0)
+		{
+			char name[20000];
+			/* found function declaration */
+			if(strcmp(scope,"GLOBAL")==0)
+			{
+				/* remaining parameters are name {USEFP, NOFP}  */
+
+				funclist_hash_key_t *flhk=(funclist_hash_key_t*)spri_allocate_type(sizeof(funclist_hash_key_t));
+				funclist_hash_value_t *flhv=(funclist_hash_value_t*)spri_allocate_type(sizeof(funclist_hash_value_t));
+	
+				ignore_result(fscanf(fin,"%s", name));
+				flhk->name=spri_strdup(name);
+				flhv->pc=addr;
+//				STRATA_LOG("annot","Adding name=%s pc=%x to funclist hash table\n", flhk->name, flhv->pc);
+				printf("Adding name=%s pc=%x to funclist hash table\n", flhk->name, flhv->pc);
+				Hashtable_put(funclists_hash, flhk, flhv);	
+			}
+			else if(strcmp(scope,"FRAMERESTORE")==0)
+			{
+				char zz[1000];
+				int reg_num, reg_offset, reg_type;
+				int reg=0;
+				for( ; reg<8;reg++)
+				{
+					ignore_result(fscanf(fin, "%d %d %d", &reg_num, &reg_offset, &reg_type));
+					assert(reg_num==reg);
+					frame_restore_hash_add_reg_restore(addr,reg_num,reg_offset,reg_type);
+				}
+				ignore_result(fscanf(fin, "%s", zz));
+				assert(strcmp("ZZ", zz)==0);
+			}
+			else if(strcmp(scope,"MMSAFENESS")==0)
+			{
+				char safeness[1000];
+				ignore_result(fscanf(fin, "%s", safeness));
+				if(strcmp(safeness, "SAFE"))
+					frame_restore_hash_set_safe_bit(addr,TRUE);
+				else if(strcmp(safeness, "SPECSAFE"))
+					frame_restore_hash_set_safe_bit(addr,TRUE);
+				else if(strcmp(safeness, "UNSAFE"))
+					frame_restore_hash_set_safe_bit(addr,FALSE);
+				else
+					fprintf(stderr,"Do not understand safeness terminoligy '%s' at line %d\n", safeness, line);
+			}
+			else
+				fprintf(stderr,"Do not understand type terminoligy '%s' at line %d\n", type, line);
+		}
+		else if(strcmp(type,"MEMORYHOLE")==0)
+		{
+
+			char esp[1000];
+			char plus[1000];
+			int offset;
+			char name[1000];
+			/* found function declaration */
+			assert(strcmp(scope,"STACK")==0);
+			/* remaining parameters are "esp + <const> <name>"  */
+			ignore_result(fscanf(fin, "%s%s%d%s", esp, plus, &offset, name));
+
+			if(strcmp(name, "ReturnAddress")==0)
+			{
+				frame_restore_set_return_address(addr,offset);	
+			}
+	
+			//printf("MEMORYHOLE, pc=%x offset=%d\n", addr, offset);
+			/* ignoring for now */
+		}
+		else if(strcmp(type,"LOCALFRAME")==0 || strcmp(type,"INARGS")==0)
+		{
+			stackref_hash_key_t *sshk=(stackref_hash_key_t*)spri_allocate_type(sizeof(stackref_hash_key_t));
+			stackref_hash_value_t *sshv=(stackref_hash_value_t*)spri_allocate_type(sizeof(stackref_hash_value_t));
+			assert(strcmp(scope,"STACK")==0);
+			/* remaining parameters are "esp + 0 {optional LocalVars} {optional instruction}" */
+			
+
+			/* add to hashtable, a name would be nice someday */
+			sshk->pc=addr;
+			sshv->size=size_type_u.size;
+			// printf("Adding pc=%x size=%d to stackref hash table\n", sshk->pc, sshv->size);
+
+//			STRATA_LOG("annot","Adding pc=%x size=%d to stackref hash table\n", sshk->pc, sshv->size);
+			Hashtable_put(stackrefs_hash, sshk,sshv);	
+
+		}
+		else if(strcmp(type,"INSTR")==0)
+		{
+			/* optimizing annotation about not needing heavyweight metadata update */
+			/* ignore for now */
+
+
+            		/*
+	 		 *  sudeep -- added support for flags
+			 */
+            		if (strcmp(scope, "RET_SAFE") == 0)
+			{
+			}
+            		else if (strcmp(scope, "DEADREGS") == 0)
+            		{
+				// stackref_hash_key_t sshk;
+				// stackref_hash_value_t *sshv;
+				// sshk.pc = addr;
+				if (Hashtable_get(stackrefs_hash, &addr))
+				{
+					// printf("STACK ALLOC INSTRUCTION CONFIRMED AT pc=0x%x size=%d\n", sshk.pc, size_type_u);
+				}
+				
+#ifdef OLD_MEDS
+                    		char regname[100];
+                    		int value = SAVE_EBP | SAVE_EDI | SAVE_ESI | SAVE_EDX | SAVE_ECX | SAVE_EBX | SAVE_EAX | SAVE_EFLAGS;
+                    		do 
+				{
+                            		ignore_result(fscanf(fin, "%s", &regname));
+                            		if (strcmp(regname, "EFLAGS") == 0)
+                                    		value ^= SAVE_EFLAGS;
+                            		else if (strcmp(regname, "EAX") == 0)
+                                    		value ^= SAVE_EAX;
+                            		else if (strcmp(regname, "EBX") == 0)
+                                    		value ^= SAVE_EBX;
+                            		else if (strcmp(regname, "ECX") == 0)
+                                    		value ^= SAVE_ECX;
+                            		else if (strcmp(regname, "EDX") == 0)
+                                    		value ^= SAVE_EDX;
+                            		else if (strcmp(regname, "ESI") == 0)
+                                    		value ^= SAVE_ESI;
+                            		else if (strcmp(regname, "EDI") == 0)
+                                    		value ^= SAVE_EDI;
+                            		else if (strcmp(regname, "EBP") == 0)
+                                    		value ^= SAVE_EBP;
+                    		} while (strcmp(regname, "ZZ"));
+                    		register_hash_key_t* key = spri_allocate_type(sizeof(register_hash_key_t));
+                    		register_hash_value_t* val = spri_allocate_type(sizeof(register_hash_value_t));
+                    		key->pc = addr;
+                    		val->value = value; 
+                    		Hashtable_put(register_hash,key,val); 
+#endif
+            		}
+            		else if (strcmp(scope, "INDIRECTCALL") == 0)
+			{
+				/* ignore INSTR INDIRECTCALL annotations, profiler generated, analyzer uses only */
+			}
+#ifdef OLD_MEDS
+            		else if (strcmp(scope, "FAULT") == 0)
+			{
+				int count;
+				ignore_result(fscanf(fin, "%d", &count));
+				recordfault_add_fault(addr,count);
+			}
+            		else if (strcmp(scope, "CHILDACCESS") == 0)
+			{
+				char start[100];
+				char end[100];
+				int istart, iend;
+				do
+				{
+					ignore_result(fscanf(fin, "%s", start));
+					if(strcmp(start,"ZZ")==0)
+						break;
+					ignore_result(fscanf(fin, "%s", end));
+					istart=atoi(start);
+					iend=atoi(end);
+					add_fgrange(addr, istart, istart+iend-1);
+				}
+				while(1);
+				
+			}
+#endif
+            		else if (strcmp(scope, "BELONGTO") == 0)
+			{
+				VirtualOffset_t func_addr;
+				unsigned int tmp=0;
+				ignore_result(fscanf(fin, "%x", &tmp));
+				func_addr=tmp;
+                    		instrmap_hash_key_t* key = (instrmap_hash_key_t*)spri_allocate_type(sizeof(instrmap_hash_key_t));
+                    		instrmap_hash_value_t* val = (instrmap_hash_value_t*)spri_allocate_type(sizeof(instrmap_hash_value_t));
+                    		key->pc = addr;
+                    		val->func_addr = func_addr; 
+                    		Hashtable_put(instrmaps_hash,key,val); 
+			}
+#ifdef OLD_MEDS
+            		else if (strcmp(scope, "PROF_FIELD") == 0)
+			{
+				int num_elems_in_hex_rep=0;
+				int i=0;
+				int j=0;
+				unsigned int cur_element=0;
+				profiler_data_hash_value_t* pdhv=NULL;
+				bitvector_t * the_read_in_bitvec=NULL;
+				char * the_bitvector=NULL;
+				char temp_obj_name[1000];
+				/* This case catches profiler fields information */
+	
+				/*
+					Read the rest of the line (format below):
+					PC 0 PROF_FIELD objname pid var_length bitvector_size_bits bitvector
+			 	*/
+	
+				/* copy scope to objname */
+				ignore_result(fscanf(fin, "%s", temp_obj_name));
+				objname=spri_strdup(temp_obj_name);
+	
+				/* lookup in hash table */
+				pdhv=get_profiler_data(addr, objname);
+	
+	
+	/* FIXME:  if bit vector dumped as hex */
+	
+				/* allocate memory for the bitvector */
+				ignore_result(fscanf(fin, "%d%d", &pid, &var_length));
+				if(var_length>0)
+				{
+					ignore_result(fscanf(fin, "%d%d", &bitvector_size_bits, &num_elems_in_hex_rep));
+	
+					the_bitvector= spri_allocate_type(((bitvector_size_bits/8)+1)*sizeof(char) + 4);
+	
+					/* read the values in to the bit vector */
+					for(i=0, j=0; i < num_elems_in_hex_rep; i++, j+=4)
+					{
+						/* read an int */
+						ignore_result(fscanf(fin, "%x", &the_bitvector[j]));
+					
+					}
+					/* create a bitvector structure to hold the info */
+					the_read_in_bitvec=spri_allocate_type(sizeof(bitvector_t));
+					the_read_in_bitvec->the_bits=the_bitvector;
+					the_read_in_bitvec->size=bitvector_size_bits;
+					the_read_in_bitvec->num_bytes=(bitvector_size_bits/8)+1;
+	
+				}
+	
+	
+	
+				/* merge the bit vector with the bitvector found in the hash table, if found */
+				/* if found */
+				if(pdhv)
+				{
+					if(var_length>0)
+					{
+						int i=0;
+						for (i=0; i<bitvector_size_bits;i++)
+						{
+							/* if the bit is 1, then set it 
+					 		* in the merged version
+					 		*/
+							if(get_bit(the_read_in_bitvec,i))
+							{
+								set_bitvector(pdhv->data_bitvector, i);
+							}
+		
+						}
+						/* in this case, we can free the_red_in_bitvec */
+						free_bitvector(the_read_in_bitvec);
+					}
+				}
+				else /* not found, add it to the hash table */
+				{
+					/* add to the profiler_data_hash table */
+					add_profiler_data(addr, objname, var_length, the_read_in_bitvec);
+				}
+
+
+			}
+#endif
+            		else 
+            		{
+              			assert(strcmp(scope,"LOCAL")==0);
+
+                    		switch(annot_type)
+                    		{
+					/* No Meta Data Updates */
+					case -1:	/* no meta data updates */
+							/* remaining params: <reason> comment */
+					{
+#ifdef OLD_MEDS
+						nometa_hash_key_t *nmhk=spri_allocate_type(sizeof(nometa_hash_key_t));
+						nometa_hash_value_t *nmhv
+							=spri_allocate_type(sizeof(nometa_hash_value_t));
+	
+						/* add to hashtable, a name would be nice someday */
+						nmhk->pc=addr;
+//						STRATA_LOG("annot","Adding nometa=%x to nowarn hash\n", nmhk->pc);
+						Hashtable_put(nometas_hash, nmhk,nmhv);	
+						break;
+#endif
+					}
+	
+					/* fast updates */
+					case -2:	/* fast meta data updates, results = always number */
+							/* remaining params: <reason> reg, {reg, ...} ZZ comment */
+					{
+#ifdef OLD_MEDS
+						char n_buffer[1000], reg_buffer[1000];
+						reg_buffer[0]=0;
+						int reg_map=0;
+
+						ignore_result(fscanf(fin, "%s", n_buffer));
+						assert(strcmp(n_buffer,"n")==0);
+
+						while(1)	// loop until we find a ZZ 
+						{
+							ignore_result(fscanf(fin, "%s", reg_buffer));
+							if(strcmp(reg_buffer,"EAX")==0 || strcmp(reg_buffer,"AL")==0
+							   || strcmp(reg_buffer,"AH")==0 || strcmp(reg_buffer,"AX")==0)
+							{
+								reg_map|=SET_EAX;
+							}
+							else if(strcmp(reg_buffer,"EBX")==0 || strcmp(reg_buffer,"BL")==0
+							   || strcmp(reg_buffer,"BH")==0 || strcmp(reg_buffer,"BX")==0)
+							{
+								reg_map|=SET_EBX;
+							}
+							else if(strcmp(reg_buffer,"ECX")==0 || strcmp(reg_buffer,"CL")==0
+							   || strcmp(reg_buffer,"CH")==0 || strcmp(reg_buffer,"CX")==0)
+							{
+								reg_map|=SET_ECX;
+							}
+							else if(strcmp(reg_buffer,"EDX")==0 || strcmp(reg_buffer,"DL")==0
+							   || strcmp(reg_buffer,"DH")==0 || strcmp(reg_buffer,"DX")==0)
+							{
+								reg_map|=SET_EDX;
+							}
+							else if(strcmp(reg_buffer,"EDI")==0)
+							{
+								reg_map|=SET_EDI;
+							}
+							else if(strcmp(reg_buffer,"ESI")==0)
+							{
+								reg_map|=SET_ESI;
+							}
+							else if(strcmp(reg_buffer,"EBP")==0)
+							{
+								reg_map|=SET_EBP;
+							}
+							else if(strcmp(reg_buffer,"ZZ")==0)
+							{
+								break;
+							}
+							else
+								assert(0);
+						}
+                    				fast_update_hash_key_t* key = spri_allocate_type(sizeof(fast_update_hash_key_t));
+                    				fast_update_hash_value_t* val = spri_allocate_type(sizeof(fast_update_hash_value_t));
+                    				key->pc = addr;
+                    				val->value = reg_map; 
+                    				Hashtable_put(fast_update_hash,key,val); 
+						
+						break;
+#endif
+					}
+
+					/* skip warning message on this instruction, promised safe */
+					case -3: 	/* remaining params: NoWarn comment */
+					{
+#ifdef OLD_MEDS
+						nowarn_hash_key_t *nwhk=spri_allocate_type(sizeof(nowarn_hash_key_t));
+						nowarn_hash_value_t *nwhv
+							=spri_allocate_type(sizeof(nowarn_hash_value_t));
+	
+						/* add to hashtable, a name would be nice someday */
+						nwhk->pc=addr;
+						STRATA_LOG("annot","Adding nowarn=%x to nowarn hash\n", nwhk->pc);
+						Hashtable_put(nowarns_hash, nwhk,nwhv);	
+#endif
+						break;
+					}
+					case -4 : // Introducing a new SizeOrtype id
+						  // for safe returns	
+					{
+						// Safe returns come here not
+						// SDT not handling them right
+						// now 
+						break;
+					}
+					default:
+						fprintf(stderr,"Unknown optimizing annotation type %d at line %d of %s",
+							size_type_u.type, line, fn);
+				}
+            		}
+			
+		
+		
+		}
+                else if(strcmp(type,"PTRIMMEDEBP")==0 || 
+			strcmp(type,"PTRIMMEDESP")==0 || 
+			strcmp(type,"PTRIMMEDESP2")==0 || 
+			strcmp(type,"PTRIMMEDABSOLUTE")==0
+		       )
+		{
+                        int the_const;
+                        int real_const=0;
+			char field[100];
+			constant_hash_key_t *chk=(constant_hash_key_t*)spri_allocate_type(sizeof(constant_hash_key_t));
+			constant_hash_value_t *chv=(constant_hash_value_t*)spri_allocate_type(sizeof(constant_hash_value_t));
+			assert(strcmp(scope,"STACK")==0 || strcmp(scope,"GLOBAL")==0);
+
+			/* remaining params are <const> <field> <real_const_if_global> <comment> */ 
+			ignore_result(fscanf(fin, "%d %s", &the_const, field));
+			if( 	strcmp(type,"PTRIMMEDESP2")==0 || 
+				strcmp(type,"PTRIMMEDABSOLUTE")==0
+			  )
+				ignore_result(fscanf(fin, "%x", &real_const));
+			else
+				real_const=the_const;
+
+			/* set the addr, and const */
+			chk->pc=addr;
+			chk->the_const=the_const;
+
+			/* set the field */
+			if(strcmp(field,"displ")==0) chk->field=chf_DISPLACEMENT;
+			else if(strcmp(field,"immed")==0) chk->field=chf_IMMEDIATE;
+			else if(strcmp(field,"other")==0) chk->field=chf_OTHER;
+			else 			     assert(0);
+
+			/* set the type */
+			if(strcmp(type,"PTRIMMEDEBP")==0 ) chv->type=cht_EBP;
+			else if(strcmp(type,"PTRIMMEDESP")==0 ) chv->type=cht_ESP;
+			else if(strcmp(type,"PTRIMMEDESP2")==0 ) chv->type=cht_ESP;
+			else if(strcmp(type,"PTRIMMEDABSOLUTE")==0 ) chv->type=cht_GLOBAL;
+			else assert(0);
+		
+			/* set the real constant */
+			chv->real_const=real_const;
+			
+			/* add to hashtable */
+//			STRATA_LOG("annot","Adding %x:%d type=%d to constant hash table\n", chk->pc, chk->the_const, chv->type );
+			Hashtable_put(constants_hash, chk,chv);	
+			
+		}
+		else if(strcmp(type,"DATAREF")==0)
+		{
+			char /* name[1000], */ parent_child[1000], offset_str[1000];
+			int id /*, parent_id, offset, parent_offset*/;
+			if(size_type_u.size<=0)
+			{
+//				STRATA_LOG("warn", "Found DATAREF of size <=0 at line %d of annot file\n", line);
+			}
+			else if(strcmp(scope,"GLOBAL")==0)
+			{
+				/* remaining params id, addr, parent/child, name */
+				unsigned int tmp=0;
+				ignore_result(fscanf(fin, "%d%x%s%s", &id, &tmp, parent_child, offset_str));
+				addr=tmp;
+
+				if(strcmp(parent_child, "PARENT")==0)
+				{
+#ifdef OLD_MEDS
+					ignore_result(fscanf(fin, "%s", name));
+					add_referent(spri_strdup(name),addr,size_type_u.size, 0, 0);
+
+					if(strata_opt_do_smp_fine_grain && !STRATA_LOG_IS_ON("no_fine_grain_static"))
+						add_to_referent_id_map(id,find_referent(addr));
+#endif
+				}
+				else if(strcmp(parent_child, "CHILDOF")==0)
+				{
+#ifdef OLD_MEDS
+					if(strata_opt_do_smp_fine_grain && !STRATA_LOG_IS_ON("no_fine_grain_static"))
+					{
+						referent_object_t* new_ref;
+						ignore_result(fscanf(fin, "%d%s%d", &parent_id, offset_str, parent_offset));
+						assert(strcmp("OFFSET", offset_str)==0);
+						referent_object_t *refnt=get_referent_from_id_map(parent_id);
+						new_ref=add_referent_field(refnt, parent_offset, addr, size_type_u.size);
+						add_to_referent_id_map(id,new_ref);
+					}
+#endif
+				}
+				else
+					assert(0);
+
+			}
+			else if(strcmp(scope,"STACK")==0)
+			{
+				char esp[1000], plus[1000]; // , offset_str[1000];
+				int esp_offset;
+
+				/* remaining params id, addr, parent/child, name */
+				ignore_result(fscanf(fin, "%d%s%s%d%s", &id, esp, plus, &esp_offset, parent_child));
+
+				assert(strcmp(esp, "esp")==0 && strcmp(plus,"+")==0);
+
+				if(strcmp(parent_child, "PARENT")==0)
+				{
+					/* add to the stackref hashtable, also record the id->stackref mapping so we can
+					 * can easily lookup the id for any fields we find.
+					 */
+                        		/*stackref_hash_value_t *sshv=(stackref_hash_value_t *)*/(void)add_stack_ref(addr,size_type_u.size, esp_offset);
+					
+					// printf("New stack frame at: pc=0x%x size=0x%x\n", addr, sshv->size);
+
+#ifdef OLD_MEDS
+					//if(strata_opt_do_smp_fine_grain && !STRATA_LOG_IS_ON("no_fine_grain_stack"))
+					// if(!STRATA_LOG_IS_ON("no_fine_grain_stack"))
+						// add_to_stackref_id_map(id,sshv);
+
+                        		/* add to hashtable, a name would be nice someday */
+                        		// STRATA_LOG("annot","Adding pc=%x size=%d to stackref hash table\n", addr, sshv->size);
+#endif
+				}
+				else if(strcmp(parent_child, "CHILDOF")==0)
+				{
+#ifdef OLD_MEDS
+					if(strata_opt_do_smp_fine_grain && !STRATA_LOG_IS_ON("no_fine_grain_stack"))
+					{
+						ignore_result(fscanf(fin, "%d%s%d", &parent_id, offset_str, &parent_offset));
+						assert(strcmp("OFFSET", offset_str)==0);
+                        			stackref_hash_value_t *sshv=get_stackref_from_id_map(parent_id);
+                        			stackref_hash_value_t *new_sshv=add_stack_ref_field(sshv, addr, 
+							size_type_u.size, parent_offset);
+						add_to_stackref_id_map(id,new_sshv);
+					}
+#endif
+				}
+				else
+					assert(0);
+			}
+
+		}
+		else if (strcmp(type,"DEALLOC")==0)
+		{
+			assert(strcmp(scope,"STACK")==0);
+			/* remaining params: comment */
+		}
+		else if(strcmp(type,"PROFILEDNUMERIC")==0)
+		{
+#ifdef OLD_MEDS
+			/* profiler generated information */
+			profile_loads_add_profile_data(addr,atoll(scope),FALSE,FALSE);
+#endif
+		}
+		else if(strcmp(type,"PROFILEDPOINTER")==0 )
+		{
+#ifdef OLD_MEDS
+			/* profiler generated information */
+			profile_loads_add_profile_data(addr,FALSE,atoll(scope),FALSE);
+#endif
+		}
+		else if(strcmp(type,"PROFILEDOTHER")==0 )
+		{
+#ifdef OLD_MEDS
+			/* profiler generated information */
+			profile_loads_add_profile_data(addr,FALSE,FALSE,atoll(scope));
+#endif
+		}
+		else if(strcmp(type,"BLOCK")==0 )
+		{
+#ifdef OLD_MEDS
+			if(strcmp(scope,"PROFILECOUNT")==0)
+			{
+				/* record that we need to profile this block */
+				profileblocks_add_profile_data(addr);
+			}
+			else if(strcmp(scope,"COUNT")==0)
+			{
+				/* do nothing */
+			}
+			else	
+			{
+//				strata_log("fatal", "Fatal, Unknown scope at line %d\n", line);
+				fprintf(stderr, "Fatal, Unknown scope at line %d\n", line);
+			}
+				
+
+#endif
+		}
+		else
+		{
+		//	strata_log("fatal", "Fatal, Unknown type at line %d\n", line);
+			fprintf(stderr, "Fatal, Unknown type at line %d\n", line);
+		}
+	
+		ignore_result(fgets(remainder, sizeof(remainder), fin));
+		line++;
+	} while(!feof(fin));
+	fclose(fin);
+}
diff --git a/irdb-lib/meds2pdb/rewriter.cpp b/irdb-lib/meds2pdb/rewriter.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..f95a60ec44e918c040210dc63aa0e11b0bc118e2
--- /dev/null
+++ b/irdb-lib/meds2pdb/rewriter.cpp
@@ -0,0 +1,873 @@
+/*
+ * Copyright (c) 2014, 2015 - University of Virginia 
+ *
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include <iostream>
+#include <fstream>
+#include <string>
+#include <set>
+#include <stdlib.h>
+#include <irdb-core>
+
+
+#include "meds_all.h"
+#include <irdb-core>
+//#include "elfio/elfio.hpp"
+
+
+#include "rewriter.h"
+
+
+using namespace std;
+using namespace IRDB_SDK;
+
+template <class T>
+void ignore_result(T /* res */) { }
+
+
+Rewriter::Rewriter(char *p_elfPath, char *p_annotationFilePath)
+{
+  m_elfReader = new ElfReader(p_elfPath);
+
+  // parse file and build up all the data structures
+  readAnnotationFile(p_annotationFilePath);
+  readElfFile(p_elfPath);
+}
+
+Rewriter::~Rewriter()
+{
+}
+
+wahoo::Function* Rewriter::ensureFunctionExists(const VirtualOffset_t p_addr)
+{
+	if (m_functions.count(p_addr) > 0)
+		return m_functions[p_addr];
+
+	wahoo::Function *fn = new wahoo::Function(p_addr);
+	m_functions[p_addr] = fn;
+
+	return fn;
+}
+
+wahoo::Instruction* Rewriter::ensureInstructionExists(const VirtualOffset_t p_addr)
+{
+	if (m_instructions.count(p_addr) > 0)
+		return m_instructions[p_addr];
+
+    wahoo::Instruction *instr = new wahoo::Instruction(p_addr);
+	m_instructions[p_addr] = instr;
+
+	return instr;
+}
+
+/*
+* Read MEDS annotation file and populate relevant hash table & data structures
+*/
+void Rewriter::readAnnotationFile(char p_filename[])
+{
+	FILE* fin=NULL;
+	VirtualOffset_t addr = 0, prevStackDeallocPC = 0;
+	union { int size, type;} size_type_u;
+	char type[200];
+	char scope[200];
+	char remainder[200000];
+	
+	
+	
+	
+	int line=0;
+
+	wahoo::Function *nullfn = new wahoo::Function("ThisIsNotAFunction", 0, 0);
+	m_functions[0]=nullfn;
+
+	constants_hash=	Hashtable_create(constants_compute_hash, constants_key_compare);
+	stackrefs_hash=	Hashtable_create(stackrefs_compute_hash, stackrefs_key_compare);
+	framerestores_hash=	Hashtable_create(framerestores_compute_hash, framerestores_key_compare);
+	instrmaps_hash=	Hashtable_create(instrmaps_compute_hash, instrmaps_key_compare);
+	funclists_hash=	Hashtable_create(funclists_compute_hash, funclists_key_compare);
+
+	if(p_filename[0]==0)
+		return;
+
+	fin=fopen(p_filename, "r");
+
+	if(!fin)
+	{
+		fprintf(stderr,"Cannot open strata annotation file %s\n", p_filename);
+		goto after_loop;
+	}
+
+	do 
+	{
+		ignore_result(fscanf(fin, "%p%d", (void**)&addr, &size_type_u.size));
+
+		if(feof(fin))		// deal with blank lines at the EOF
+			break;
+		
+		ignore_result(fscanf(fin, "%s%s", type,scope));
+
+		int annot_type;
+		if(size_type_u.type<-255)
+		{
+			annot_type=size_type_u.type+256;
+			size_type_u.type=size_type_u.type+256;
+		}
+		else
+			annot_type=size_type_u.type;
+
+//		fprintf(stderr,"main loop: addr 0x%p   scope: %s\n", addr, scope);
+
+		/* if the size > 0, then this is a declaration of a variable */
+		if(strcmp(type,"FUNC")==0)
+		{
+			prevStackDeallocPC = 0;
+
+			char name[20000];
+			/* found function declaration */
+			if(strcmp(scope,"GLOBAL")==0 || strcmp(scope,"LOCAL")==0)
+			{
+//   8048250     94 FUNC GLOBAL readString_xxx FUNC_UNSAFE USEFP RET    80482ad
+				/* remaining parameters are name {USEFP, NOFP}  */
+
+				funclist_hash_key_t *flhk=(funclist_hash_key_t*)spri_allocate_type(sizeof(funclist_hash_key_t));
+				funclist_hash_value_t *flhv=(funclist_hash_value_t*)spri_allocate_type(sizeof(funclist_hash_value_t));
+	
+				ignore_result(fscanf(fin,"%s", name));
+				flhk->name=spri_strdup(name);
+				flhv->pc=addr;
+//				fprintf(stderr, "Adding name=%s pc=%x to funclist hash table\n", flhk->name, flhv->pc);
+				Hashtable_put(funclists_hash, flhk, flhv);	
+
+				wahoo::Function *fn = ensureFunctionExists(addr);
+				fn->setAddress(addr);
+				fn->setSize(size_type_u.size);
+				fn->setName(name);
+//				wahoo::Function *fn = new wahoo::Function(name, addr, size_type_u.size);
+				ignore_result(fgets(remainder, sizeof(remainder), fin));
+				if (strstr(remainder, "FUNC_SAFE"))
+					fn->setSafe();
+				else
+					fn->setUnsafe();
+
+				if (strstr(remainder, "USEFP"))
+					fn->setUseFramePointer(true);
+
+				m_functions[addr] = fn;
+
+				line++;
+				continue;
+			}
+			else if(strcmp(scope,"FRAMERESTORE")==0)
+			{
+				char zz[1000];
+				int reg_num, reg_offset, reg_type;
+				int reg=0;
+
+				while(1)	// loop until found ZZ 
+				{
+					ignore_result(fscanf(fin, "%s", zz));
+					if(strcmp("ZZ", zz)==0)
+						break;
+			
+					reg_num=atoi(zz);
+					ignore_result(fscanf(fin,"%d%d", &reg_offset, &reg_type));
+					assert(reg_num==reg);
+					frame_restore_hash_add_reg_restore(addr,reg_num,reg_offset,reg_type);
+					reg++;
+				}
+			}
+			else if(strcmp(scope,"MMSAFENESS")==0)
+			{
+			char safeness[1000];
+			ignore_result(fscanf(fin, "%s", safeness));
+			if(strcmp(safeness, "SAFE") == 0)
+ 			{
+//
+// 20110315 Anh
+// bug in MEDS re. FUNCTION SAFENESS, the annotation file sometimes mark a function as
+// SAFE when in fact it isn't
+//					m_functions[addr]->setSafe();
+					frame_restore_hash_set_safe_bit(addr,TRUE);
+				}
+				else if(strcmp(safeness, "SPECSAFE") == 0)
+				{
+//					m_functions[addr]->setSafe();
+					frame_restore_hash_set_safe_bit(addr,TRUE);
+				}
+				else if(strcmp(safeness, "UNSAFE") == 0)
+					frame_restore_hash_set_safe_bit(addr,FALSE);
+				else
+					fprintf(stderr,"Do not understand safeness terminology '%s' at line %d\n", safeness, line);
+			}
+			else
+				fprintf(stderr,"Do not understand type terminology '%s' at line %d\n", type, line);
+		}
+		else if(strcmp(type,"MEMORYHOLE")==0)
+		{
+			char esp[1000];
+			char plus[1000];
+			int offset;
+			char name[1000];
+			/* found function declaration */
+			assert(strcmp(scope,"STACK")==0);
+			/* remaining parameters are "esp + <const> <name>"  */
+			ignore_result(fscanf(fin, "%s%s%d%s", esp, plus, &offset, name));
+
+			if(strcmp(name, "ReturnAddress")==0)
+			{
+				frame_restore_set_return_address(addr,offset);	
+			}
+	
+//			printf("MEMORYHOLE, pc=%x offset=%d\n", addr, offset);
+			/* ignoring for now */
+		}
+		else if(strcmp(type,"LOCALFRAME")==0 || strcmp(type,"INARGS")==0)
+		{
+			stackref_hash_key_t *sshk=(stackref_hash_key_t*)spri_allocate_type(sizeof(stackref_hash_key_t));
+			stackref_hash_value_t *sshv=(stackref_hash_value_t*)spri_allocate_type(sizeof(stackref_hash_value_t));
+			assert(strcmp(scope,"STACK")==0);
+			/* remaining parameters are "esp + 0 {optional LocalVars} {optional instruction}" */
+			
+
+			/* add to hashtable, a name would be nice someday */
+			sshk->pc=addr;
+			sshv->size=size_type_u.size;
+//			printf("Adding pc=%x size=%d to stackref hash table\n", sshk->pc, sshv->size);
+
+			Hashtable_put(stackrefs_hash, sshk,sshv);	
+
+		}
+		else if(strcmp(type,"INSTR")==0)
+		{
+//fprintf(stderr, "INSTR: At %p, handling %s -- scope:%s\n", addr, type, scope);
+
+			/* optimizing annotation about not needing heavyweight metadata update */
+			/* ignore for now */
+			
+            		/*
+	 		 *  sudeep -- added support for flags
+			 */
+            		if (strcmp(scope, "RET_SAFE") == 0)
+			{
+			}
+            		else if (strcmp(scope, "DEADREGS") == 0)
+            		{
+				stackref_hash_key_t sshk;
+				stackref_hash_value_t *sshv;
+				sshk.pc = addr;
+				ensureInstructionExists(addr);
+				m_instructions[addr]->setSize(size_type_u.size);
+				sshv = (stackref_hash_value_t*) Hashtable_get(stackrefs_hash, &sshk);
+				if (sshv)
+				{
+                    		        instrmap_hash_key_t key;
+                                        key.pc = addr;
+                    		        instrmap_hash_value_t* val;
+//					printf("STACK ALLOC INSTRUCTION CONFIRMED AT pc=0x%x size=%d\n", sshk.pc, size_type_u.size);
+				        val = (instrmap_hash_value_t*) Hashtable_get(instrmaps_hash, &key);
+				        if (val)
+                                        {
+//					  printf("STACK ALLOC INSTRUCTION CONFIRMED: site alloc marked\n");
+                                          val->site_alloc = 1; 
+                                          val->size = size_type_u.size; 
+                                        }
+
+					m_instructions[addr]->markAllocSite();
+					m_instructions[addr]->setSize(size_type_u.size);
+				}
+				else if (size_type_u.size == 1)
+				{
+					// keep track of 1 byte instruction
+                    			instrmap_hash_key_t* key = (instrmap_hash_key_t*)spri_allocate_type(sizeof(instrmap_hash_key_t));
+	                    		instrmap_hash_value_t* val = (instrmap_hash_value_t*)spri_allocate_type(sizeof(instrmap_hash_value_t));
+       		             		key->pc = addr;
+                       		        val->site_alloc = 0;
+                                        val->size = size_type_u.size; 
+	                    		Hashtable_put(instrmaps_hash,key,val); 
+
+					ignore_result(fgets(remainder, sizeof(remainder), fin));
+					// this is a *potential* stack deallocation instruction only
+					if ((strstr(remainder,"leave") && strstr(remainder,"EFLAGS")) ||
+ 					    (strstr(remainder,"pop"  ) && strstr(remainder,"ebp"   ))
+					   )
+					{
+						prevStackDeallocPC = addr;
+					}
+
+					// b/c we ate up <remainder> we have to do this
+					line++;
+					continue;
+						
+				}
+				
+            		}
+            		else if (strcmp(scope, "INDIRECTCALL") == 0)
+			{
+				/* ignore INSTR INDIRECTCALL annotations, profiler generated, analyzer uses only */
+			}
+			else if (strcmp(scope, "BELONGTO") == 0)
+			{
+				VirtualOffset_t func_addr;
+				ignore_result(fscanf(fin, "%p", (void**)&func_addr));
+                    		instrmap_hash_key_t* key = (instrmap_hash_key_t*)spri_allocate_type(sizeof(instrmap_hash_key_t));
+                    		instrmap_hash_value_t* val = (instrmap_hash_value_t*)spri_allocate_type(sizeof(instrmap_hash_value_t));
+                    		key->pc = addr;
+                    		val->func_addr = func_addr; 
+                                val->site_alloc = 0;
+                                val->size = 0;
+                    		Hashtable_put(instrmaps_hash,key,val); 
+
+				// rely on the fact that INST BELONGTO is the first INST annotation in a MEDS file (warning: but it is not required to be there)
+//				assert(m_functions[func_addr]);
+				ignore_result(ensureFunctionExists(func_addr));
+				wahoo::Instruction* instr = new wahoo::Instruction(addr, -1, m_functions[func_addr]);
+				m_instructions[addr] = instr;
+
+				// associate instruction with its enclosing function
+				m_functions[func_addr]->addInstruction(instr);
+//fprintf(stderr,"0x%08x belongs to function %s\n", addr, m_functions[func_addr]->getName().c_str());
+			} 
+			else
+			{
+
+              			assert(strcmp(scope,"LOCAL")==0);
+						ensureInstructionExists(addr);
+
+/*
+                        	if (!m_instructions[addr])
+                        	{
+                                	// unknown size, unknown function
+                                	wahoo::Instruction* instr = new wahoo::Instruction(addr, -1, NULL);
+                                	m_instructions[addr] = instr;
+                        	}
+*/
+
+                    		switch(annot_type)
+                    		{
+					/* No Meta Data Updates */
+					case -1:	/* no meta data updates */
+							/* remaining params: <reason> comment */
+					{
+						ignore_result(fgets(remainder, sizeof(remainder), fin));
+						// this is a *potential* stack deallocation instruction only
+						if (strstr(remainder,"add") && strstr(remainder,"esp")
+							&& strstr(remainder,"1stSrcVia2ndSrc")
+							&& strstr(remainder,"IMMEDNUM"))
+						{
+							prevStackDeallocPC = addr;
+						}
+						else if (strstr(remainder,"SafeFrameAlloc") 
+							&& strstr(remainder,"sub")
+							&& strstr(remainder,"esp"))
+						{
+							m_instructions[addr]->markAllocSite();
+						}
+						else if (strstr(remainder,"[ebp+") 
+ 							&& strstr(remainder,"var_"))
+						{
+/*
+MEDS doesn't mark this as a stack reference
+   8048281      0 INSTR BELONGTO 8048262
+   8048281     -1 INSTR LOCAL MetadataRedundant mov     eax, [ebp+var_4]
+*/
+							m_instructions[addr]->markStackRef();
+							m_instructions[addr]->markVarStackRef();
+						}
+						else if (strstr(remainder,"[esp+") 
+ 							&& (strstr(remainder,"var_") || strstr(remainder, "arg_")))
+						{
+							m_instructions[addr]->markStackRef();
+							m_instructions[addr]->markVarStackRef();
+						}
+			
+
+						// b/c we ate up <remainder> we have to do this
+						line++;
+						continue;
+						
+					}
+	
+					/* fast updates */
+					case -2:	/* fast meta data updates, results = always number */
+							/* remaining params: <reason> reg, {reg, ...} ZZ comment */
+					{
+						break;
+					}
+
+					/* skip warning message on this instruction, promised safe */
+					case -3: 	/* remaining params: NoWarn comment */
+					{
+						break;
+					}
+					case -4 : // Introducing a new SizeOrtype id
+						  // for safe returns	
+					{
+						// Safe returns come here not
+						// SDT not handling them right
+						// now 
+						break;
+					}
+					default:
+						fprintf(stderr,"Unknown optimizing annotation type %d at line %d of %s",
+							size_type_u.type, line, p_filename);
+				}
+            		}
+			
+		
+		
+		}
+                else if(strcmp(type,"PTRIMMEDEBP")==0 || 
+			strcmp(type,"PTRIMMEDESP")==0 || 
+			strcmp(type,"PTRIMMEDESP2")==0 || 
+			strcmp(type,"PTRIMMEDABSOLUTE")==0
+		       )
+		{
+                        int the_const;
+                        int real_const=0;
+			char field[100];
+			constant_hash_key_t *chk=(constant_hash_key_t*)spri_allocate_type(sizeof(constant_hash_key_t));
+			constant_hash_value_t *chv=(constant_hash_value_t*)spri_allocate_type(sizeof(constant_hash_value_t));
+			assert(strcmp(scope,"STACK")==0 || strcmp(scope,"GLOBAL")==0);
+
+			/* remaining params are <const> <field> <real_const_if_global> <comment> */ 
+			ignore_result(fscanf(fin, "%d%s", &the_const, field));
+			if( 	strcmp(type,"PTRIMMEDESP2")==0 || 
+				strcmp(type,"PTRIMMEDABSOLUTE")==0
+			  )
+				ignore_result(fscanf(fin, "%x", &real_const));
+			else
+				real_const=the_const;
+
+			/* set the addr, and const */
+			chk->pc=addr;
+			chk->the_const=the_const;
+
+			/* set the field */
+			if(strcmp(field,"displ")==0) chk->field=chf_DISPLACEMENT;
+			else if(strcmp(field,"immed")==0) chk->field=chf_IMMEDIATE;
+			else if(strcmp(field,"other")==0) chk->field=chf_OTHER;
+			else 			     assert(0);
+
+			/* set the type */
+			if(strcmp(type,"PTRIMMEDEBP")==0 ) chv->type=cht_EBP;
+			else if(strcmp(type,"PTRIMMEDESP")==0 ) chv->type=cht_ESP;
+			else if(strcmp(type,"PTRIMMEDESP2")==0 ) chv->type=cht_ESP;
+			else if(strcmp(type,"PTRIMMEDABSOLUTE")==0 ) chv->type=cht_GLOBAL;
+			else assert(0);
+		
+			/* set the real constant */
+			chv->real_const=real_const;
+			
+			/* add to hashtable */
+			Hashtable_put(constants_hash, chk,chv);	
+	
+			ensureInstructionExists(addr);
+/*
+			if (!m_instructions[addr])
+			{
+ 				// unknown size, unknown function
+				wahoo::Instruction* instr = new wahoo::Instruction(addr, -1, NULL);
+				m_instructions[addr] = instr;
+			}
+*/
+
+//			fprintf(stderr,"@ 0x%x marking instruction as stack reference\n", addr);
+			m_instructions[addr]->markStackRef();
+			m_instructions[addr]->setSize(size_type_u.size);
+
+                        // see if we can pick up access to local variables
+			// and access to arguments off esp
+			ignore_result(fgets(remainder, sizeof(remainder), fin));
+			if (strstr(remainder, "var_") || 
+                            (strstr(remainder, "arg_") && strstr(remainder, "[esp")))
+			{
+				m_instructions[addr]->markVarStackRef();
+ 			}
+			
+
+			// b/c we ate up <remainder> we have to do this
+			line++;
+			continue;
+		}
+		else if(strcmp(type,"DATAREF")==0)
+		{
+			char parent_child[1000];
+			int id;
+			if(size_type_u.size<=0)
+			{
+			}
+			else if(strcmp(scope,"GLOBAL")==0)
+			{
+				/* remaining params id, addr, parent/child, name */
+				ignore_result(fscanf(fin, "%d%p%s", &id, (void**)&addr, parent_child));
+
+				if(strcmp(parent_child, "PARENT")==0)
+				{
+				}
+				else if(strcmp(parent_child, "CHILDOF")==0)
+				{
+				}
+				else
+					assert(0);
+
+			}
+			else if(strcmp(scope,"STACK")==0)
+			{
+				char esp[1000], plus[1000], name[1000];
+				int esp_offset;
+
+				/* remaining params id, addr, parent/child, name */
+				ignore_result(fscanf(fin, "%d%s%s%d%s%s", &id, esp, plus, &esp_offset, parent_child, name));
+
+				assert(strcmp(esp, "esp")==0 && strcmp(plus,"+")==0);
+
+				if(strcmp(parent_child, "PARENT")==0)
+				{
+					/* add to the stackref hashtable, also record the id->stackref mapping so we can
+					 * can easily lookup the id for any fields we find.
+					 */
+                        		ignore_result(add_stack_ref(addr,size_type_u.size, esp_offset));
+					
+
+					// @todo: record frame size
+					// set the frame size
+// 5b     64 DATAREF STACK 2 esp + 0 PARENT LocalFrame LOCALFRAME
+					if (strstr(name,"LocalFrame"))
+					{
+						if ( m_instructions[addr]->getFunction() )
+							m_instructions[addr]->getFunction()->setFrameSize(size_type_u.size);
+					}
+
+				}
+				else if(strcmp(parent_child, "CHILDOF")==0)
+				{
+/*
+need to pick up size of outargsregion
+any esp access within this region should not be transformed
+any esp access outside this region (esp + K) >= (esp + size) can be xformed
+
+   80482fd     28 DATAREF STACK 3123 esp + 0 CHILDOF 3122 OFFSET 0 OutArgsRegion OUTARGS
+   80482fd      4 DATAREF STACK 3124 esp + 28 CHILDOF 3122 OFFSET 28 LOCALVAR var_20
+   80482fd      4 DATAREF STACK 3125 esp + 32 CHILDOF 3122 OFFSET 32 LOCALVAR var_1C
+   80482fd      4 DATAREF STACK 3126 esp + 36 CHILDOF 3122 OFFSET 36 LOCALVAR var_18
+*/
+					ignore_result(fgets(remainder, sizeof(remainder), fin));
+					if (strstr(remainder,"OutArgsRegion"))
+					{
+//fprintf(stderr," found OutArgsRegion @ 0x%08x\n", addr);
+						ensureInstructionExists(addr);
+						assert(m_instructions[addr]->getFunction());
+						m_instructions[addr]->getFunction()->setOutArgsRegionSize(size_type_u.size);
+					}
+					line++;
+					continue;
+
+				}
+				else
+					assert(0);
+			}
+
+		}
+		else if (strcmp(type,"DEALLOC")==0)
+		{
+			assert(strcmp(scope,"STACK")==0);
+			/* remaining params: comment */
+
+			// handle the two forms of   add %esp, X
+			// for reclaiming stack space
+			if (addr - prevStackDeallocPC == 3 || addr - prevStackDeallocPC == 6)
+			{
+//				fprintf(stderr, "Detected nice stack deallocation instruction at 0x%x\n", prevStackDeallocPC);
+//				assert(m_instructions[prevStackDeallocPC]);
+				ensureInstructionExists(prevStackDeallocPC);
+				m_instructions[prevStackDeallocPC]->markDeallocSite();
+				m_instructions[prevStackDeallocPC]->setSize(addr - prevStackDeallocPC);
+			
+			}
+			// handle leave/ret
+			else if (addr - prevStackDeallocPC == 1)
+			{
+//				assert(m_instructions[prevStackDeallocPC]);
+				ensureInstructionExists(prevStackDeallocPC);
+				m_instructions[prevStackDeallocPC]->markDeallocSite();
+				m_instructions[prevStackDeallocPC]->setSize(1);
+			}
+		}
+		else if(strcmp(type,"BLOCK")==0 )
+		{
+		}
+		else
+		{
+			fprintf(stderr, "Fatal, Unknown type at line %d\n", line);
+		}
+	
+		ignore_result(fgets(remainder, sizeof(remainder), fin));
+		line++;
+	} while(!feof(fin));
+	fclose(fin);
+
+after_loop:
+
+  // for each instruction in a function, disassemble and stash away assembly string
+	disassemble();
+}
+
+
+/*
+* Read MEDS annotation file and populate relevant hash table & data structures
+*/
+void Rewriter::readElfFile(char p_filename[])
+{
+	static char buf[64*1024];
+	char* objdump=getenv("PS_OBJDUMP");
+	if(!objdump)
+		objdump=strdup("objdump");
+	sprintf(buf, "%s -d --prefix-addresses %s | grep \"^[0-9]\"", objdump, p_filename);
+	printf("Running objdump, like so: %s\n", buf);
+	FILE* pin=popen(buf, "r");
+	VirtualOffset_t addr;
+
+	assert(pin);
+
+	
+	void* tmp=NULL;
+	ignore_result(fscanf(pin, "%p", &tmp));
+	addr=(VirtualOffset_t)tmp;
+	ignore_result(fgets(buf,sizeof(buf),pin));
+	do 
+	{
+		if(m_instructions[addr]==NULL)
+		{
+			cout<<"Found instruction from objdump at "<<hex<<addr<<endl;
+			m_instructions[addr]=new wahoo::Instruction(addr,-1,NULL);
+		}
+		ignore_result(fscanf(pin,"%p", &tmp));
+		addr=(VirtualOffset_t)tmp;
+		ignore_result(fgets(buf,sizeof(buf),pin));
+	} while(!feof(pin));
+
+	pclose(pin);
+
+	disassemble();
+}
+
+
+/*
+*   for all instructions, disassemble them using the BeaEngine
+*/
+void Rewriter::disassemble()
+{
+	getElfReader()->SetArchitecture();
+	/*
+	if(getElfReader()->isElf64() || getElfReader()->isPe64())
+		FileIR_t::SetArchitectureBitWidth(64);
+	else
+		FileIR_t::SetArchitectureBitWidth(32);
+		*/
+
+  	// for every instruction, grab from ELF
+  	// disassemble
+
+	vector<wahoo::Instruction*> instructions=getAllInstructions(); 
+
+	fprintf(stderr, "Rewriter::disassemble(): number of instructions: %" PRIuPTR "\n", (uintptr_t)instructions.size());
+
+    	for (auto j = 0U; j < instructions.size(); ++j)
+    	{
+      		wahoo::Instruction *instr = instructions[j];
+
+		const auto instr_data=(void*)(getElfReader()->getInstructionBuffer(instr->getAddress()));
+		const auto p_disasm=DecodedInstruction_t::factory(instr->getAddress(), instr_data, 16);
+		const auto &disasm=*p_disasm;
+
+
+		/* maybe this isn't in a section so getInstructionBuffer returns 0 */
+
+		if(disasm.valid())
+		{
+      			const auto instr_len = disasm.length() ; //Disasm(&disasm);
+      			instr->setAsm(disasm.getDisassembly());
+      			instr->setSize(instr_len);
+      			instr->setData(instr_data);
+		}
+		else
+		{
+			cerr<<"Decided that instruction at "<<hex
+				<<instr->getAddress()<<dec<<" is bogus."<<endl;
+			/* bogus intruction, remove it */
+			m_instructions[instr->getAddress()]=NULL;
+
+			if(instr)
+				delete instr;
+		}
+    	}
+}
+
+void Rewriter::addSimpleRewriteRule(wahoo::Function* p_func, char *p_origInstr, int p_origSize, VirtualOffset_t p_origAddress, char *p_newInstr)
+{
+  char buf[1024];
+  char aspri[2048];
+  
+  aspri[0] = '\0';
+
+  sprintf(buf,"# orig(%d): %s\n", p_origSize, p_origInstr);
+  strcpy(aspri, buf);
+  sprintf(buf,"0x%8p -> .\n", (void*)p_origAddress);
+  strcat(aspri, buf);
+  sprintf(buf,". ** %s\n", p_newInstr);
+  strcat(aspri, buf);
+  sprintf(buf,". -> 0x%8p\n", (void*)(p_origAddress + p_origSize));
+  strcat(aspri, buf);
+
+  fprintf(stderr, "WOULD EMIT RULE: %s\n", aspri);
+  p_func->addRewriteRule(string(aspri));
+}
+
+// commit function to SPRI file
+void Rewriter::commitFn2SPRI(wahoo::Function *p_func, FILE *p_fp)
+{
+  if (!p_func) return;
+
+  for (auto i = 0U; i < p_func->getRewrites().size(); ++i)
+  {
+    string rewriteRule = p_func->getRewrites()[i];
+    fprintf(p_fp, "%s\n", rewriteRule.c_str());
+  }
+}
+
+vector<wahoo::Function*> Rewriter::getCandidateFunctions()
+{
+  vector<wahoo::Function*> candidates;
+  for (map<VirtualOffset_t, wahoo::Function*>::iterator it = m_functions.begin(); it != m_functions.end(); ++it)
+  {
+    wahoo::Function* f = it->second;
+
+    // null fn or fn marked as SAFE by MEDS -- we don't xform those
+    if (!f || f->isSafe()) continue;
+
+    candidates.push_back(f);
+  }
+
+  return candidates;
+}
+
+vector<wahoo::Function*> Rewriter::getNonCandidateFunctions()
+{
+  vector<wahoo::Function*> nonCandidates;
+  for (map<VirtualOffset_t, wahoo::Function*>::iterator it = m_functions.begin(); it != m_functions.end(); ++it)
+  {
+    wahoo::Function* f = it->second;
+
+    // null fn or fn marked as SAFE by MEDS -- we don't xform those
+    if (!f) continue;
+    if (f->isSafe())
+      nonCandidates.push_back(f);
+  }
+
+  return nonCandidates;
+}
+
+vector<wahoo::Function*> Rewriter::getAllFunctions()
+{
+  vector<wahoo::Function*> allFunctions;
+
+  for (map<VirtualOffset_t, wahoo::Function*>::iterator it = m_functions.begin(); it != m_functions.end(); ++it)
+  {
+    wahoo::Function* f = it->second;
+
+    if (!f) continue;
+
+    allFunctions.push_back(f);
+  }
+
+  return allFunctions;
+}
+
+vector<wahoo::Instruction*> Rewriter::getAllInstructions()
+{
+  vector<wahoo::Instruction*> allInstructions;
+
+  for (map<VirtualOffset_t, wahoo::Instruction*>::iterator it = m_instructions.begin(); it != m_instructions.end(); ++it)
+  {
+    wahoo::Instruction* instr = it->second;
+
+    if (!instr) continue;
+
+    allInstructions.push_back(instr);
+  }
+
+  return allInstructions;
+}
+
+map<wahoo::Function*, double> Rewriter::getFunctionCoverage(char *p_instructionFile)
+{
+  map<wahoo::Function*, double> coverage;
+
+  ifstream infile;
+  infile.open(p_instructionFile, ifstream::in);
+
+  if(!infile.is_open())
+  {
+    cerr << "File containing instructions visited not found:" << p_instructionFile << endl;
+    return coverage;
+  }
+
+  set<VirtualOffset_t> visitedInstructions;
+
+  infile.seekg(0,ios::end);
+  size_t size = infile.tellg();
+  infile.seekg(ios::beg);
+  if( size == 0)
+  {
+      cerr << "File containing instructions visited is empty is empty\n"<<endl;
+      return coverage;
+  }
+
+  while (infile.good())
+  {
+    int address = 0;
+    
+    infile>>hex>>address;
+
+    visitedInstructions.insert((VirtualOffset_t) address);
+  }
+
+  vector<wahoo::Instruction*> allInstructions = getAllInstructions();
+
+  for (auto i = 0U; i < allInstructions.size(); ++i)
+  {
+    wahoo::Instruction* instr = allInstructions[i];
+    if (!instr) continue;
+
+    if (visitedInstructions.count(instr->getAddress()))
+    {
+	instr->setVisited();
+    }
+  }
+
+  // now all instructions have been marked as visited or not
+
+  vector<wahoo::Function*> allFunctions = getAllFunctions();
+  for (auto i = 0U; i < allFunctions.size(); ++i)
+  {
+    coverage[allFunctions[i]] = allFunctions[i]->getInstructionCoverage();
+  }
+
+  return coverage;
+}
diff --git a/irdb-lib/meds2pdb/rewriter.h b/irdb-lib/meds2pdb/rewriter.h
new file mode 100644
index 0000000000000000000000000000000000000000..9614dbcedbd4eb3b826efca2e7056c7a2615882f
--- /dev/null
+++ b/irdb-lib/meds2pdb/rewriter.h
@@ -0,0 +1,54 @@
+#include <map>
+#include <set>
+#include <irdb-core>
+// #include "elfio/elfio.hpp"
+//#include "elfio/elfio_dump.hpp"
+
+#include "elfreader.h"
+#include "function_descriptor.h"
+
+
+using namespace std;
+
+class Rewriter
+{
+  public:
+    Rewriter(char *p_elf, char *p_annotationFile);
+    ~Rewriter();
+
+    virtual vector<wahoo::Function*> getAllFunctions();
+    virtual vector<wahoo::Function*> getCandidateFunctions();
+    virtual vector<wahoo::Function*> getNonCandidateFunctions();
+
+    virtual vector<wahoo::Instruction*> getAllInstructions();
+
+    map<wahoo::Function*, double> getFunctionCoverage(char *p_instFile); 
+
+  protected:
+    void readAnnotationFile(char []);
+    void readElfFile(char []);
+    ElfReader *getElfReader() const { return m_elfReader; }
+    FILE* getAsmSpri() { return m_spri; };
+    void setAsmSpri(FILE *p_spri) { m_spri = p_spri; };
+
+    // disassemble all functions
+    void disassemble();
+
+    // one instruction modification
+    void addSimpleRewriteRule(wahoo::Function* p_func, char *p_origInstr, int p_origSize, IRDB_SDK::VirtualOffset_t p_origAddress, char *p_newInstr);
+
+    // commit function to AsmSPRI file
+    void commitFn2SPRI(wahoo::Function* p_func, FILE *p_file);
+
+  protected:
+    map<IRDB_SDK::VirtualOffset_t, wahoo::Function*> m_functions;
+    map<IRDB_SDK::VirtualOffset_t, wahoo::Instruction*> m_instructions;
+
+  private:
+    wahoo::Function*     ensureFunctionExists(const IRDB_SDK::VirtualOffset_t);
+    wahoo::Instruction*  ensureInstructionExists(const IRDB_SDK::VirtualOffset_t);
+
+  private:
+    ElfReader*    m_elfReader;   
+    FILE*         m_spri; 
+};
diff --git a/irdb-lib/meds2pdb/spri_alloc.cpp b/irdb-lib/meds2pdb/spri_alloc.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..57a4b77e05af5467d25d9601a4226be22b05e81a
--- /dev/null
+++ b/irdb-lib/meds2pdb/spri_alloc.cpp
@@ -0,0 +1,50 @@
+/*
+ * spri_alloc.c - allocation routines, see below.
+ *
+ * Copyright (c) 2011 - Zephyr Software
+ *
+ * This file is part of the Strata dynamic code modification infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from Zephyr 
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#include <stdlib.h>
+#include <string.h>
+#include "spri_alloc.h"
+
+//
+// Wrap memory management routines
+//
+// This will make it easier to integrate back within the Strata library 
+// as we could simply call strata_allocate_type and strata_deallocate_type
+// instead of malloc/free
+//
+
+void* spri_allocate_type(int p_size)
+{
+  return malloc(p_size);
+}
+
+void* spri_deallocate_type(void *p_ptr, int p_size)
+{
+  free(p_ptr);
+  return NULL;
+}
+
+char* spri_strdup(const char *p_ptr)
+{
+  return strdup(p_ptr);
+}
diff --git a/irdb-lib/meds2pdb/spri_alloc.h b/irdb-lib/meds2pdb/spri_alloc.h
new file mode 100644
index 0000000000000000000000000000000000000000..880db71a059609c9417894dd0f07638e4bc992b8
--- /dev/null
+++ b/irdb-lib/meds2pdb/spri_alloc.h
@@ -0,0 +1,35 @@
+/*
+ * spri_alloc.h - allocation routines, see below.
+ *
+ * Copyright (c) 2011 - Zephyr Software
+ *
+ * This file is part of the Strata dynamic code modification infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from Zephyr 
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+#ifndef _SPRI_ALLOC_
+#define _SPRI_ALLOC_
+
+/*
+ *  Memory allocation/deallocation wrapper
+ */
+
+void* spri_allocate_type(int);
+void* spri_deallocate_type(void *, int);
+char* spri_strdup(const char *);
+
+#endif
diff --git a/irdb-lib/meds2pdb/stackref_hash.cpp b/irdb-lib/meds2pdb/stackref_hash.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..baba2498166443b3f7780e44300f271f3e0f7d18
--- /dev/null
+++ b/irdb-lib/meds2pdb/stackref_hash.cpp
@@ -0,0 +1,84 @@
+/*
+ * stackref_hash.c - see below.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#include "meds_all.h"
+#include "stackref_hash.h"
+
+/* 
+ * hashtable of data for stack referents 
+ */
+
+Hashtable *stackrefs_hash=NULL;
+
+long stackrefs_compute_hash(void* key1)
+{
+        stackref_hash_key_t * a_key=(stackref_hash_key_t *)key1;
+
+        return a_key->pc;
+}
+
+long stackrefs_key_compare(void* key1, void* key2)
+{
+        stackref_hash_key_t * a_key=(stackref_hash_key_t *)key1;
+        stackref_hash_key_t * b_key=(stackref_hash_key_t *)key2;
+
+        return a_key->pc == b_key->pc;
+}
+
+
+/* add something to the stackrefs_hash hashtable */
+stackref_hash_value_t *add_stack_ref(VirtualOffset_t pc,int size, int offset)
+{
+       	stackref_hash_key_t *sshk=(stackref_hash_key_t*)spri_allocate_type(sizeof(stackref_hash_key_t ));
+       	stackref_hash_value_t *sshv=(stackref_hash_value_t*)spri_allocate_type(sizeof(stackref_hash_value_t ));
+	
+       	sshk->pc=pc;
+      	sshv->esp_offset=offset;
+       	sshv->size=size;
+       	sshv->parent_stackref=NULL;
+       	sshv->child_stackref=NULL;
+       	sshv->sibling_stackref=NULL;
+
+       	Hashtable_put(stackrefs_hash, sshk, sshv);
+
+	return sshv;
+}
+
+stackref_hash_value_t *add_stack_ref_field(stackref_hash_value_t* parent, VirtualOffset_t pc, int size, int offset)
+{
+       	stackref_hash_key_t *sshk=(stackref_hash_key_t*)spri_allocate_type(sizeof(stackref_hash_key_t ));
+       	stackref_hash_value_t *sshv=(stackref_hash_value_t*)spri_allocate_type(sizeof(stackref_hash_value_t ));
+	
+       	sshk->pc=pc;
+      	sshv->esp_offset=offset;
+       	sshv->size=size;
+	sshv->parent_stackref=parent;
+       	sshv->child_stackref=NULL;
+
+	/* link into the parent's child list */
+       	sshv->sibling_stackref=parent->child_stackref;
+	parent->child_stackref=sshv;
+
+	return sshv;
+}
+
diff --git a/irdb-lib/meds2pdb/stackref_hash.h b/irdb-lib/meds2pdb/stackref_hash.h
new file mode 100644
index 0000000000000000000000000000000000000000..b5f526aa3e01c5083edb4e6a6c0651224a78ea05
--- /dev/null
+++ b/irdb-lib/meds2pdb/stackref_hash.h
@@ -0,0 +1,59 @@
+/*
+ * stackref_hash.h - see below.
+ *
+ * Copyright (c) 2000, 2001, 2010 - University of Virginia 
+ *
+ * This file is part of the Memory Error Detection System (MEDS) infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from the University 
+ * of Virginia.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: University of Virginia
+ * e-mail: jwd@virginia.com
+ * URL   : http://www.cs.virginia.edu/
+ *
+ */
+
+#ifndef stackref_hash_h
+#define stackref_hash_h
+
+#include "meds_all.h"
+
+
+/*
+ * necessary code for creating a hashtable of stack reference data
+ */
+
+extern Hashtable *stackrefs_hash;
+typedef struct stackref_hash_key stackref_hash_key_t;
+struct stackref_hash_key
+{
+        VirtualOffset_t pc;
+};
+
+typedef struct stackref_hash_value stackref_hash_value_t;
+struct stackref_hash_value
+{
+	int esp_offset;
+	int size;
+	stackref_hash_value_t *parent_stackref;
+	stackref_hash_value_t *child_stackref;
+	stackref_hash_value_t *sibling_stackref;
+};
+
+long stackrefs_compute_hash(void* key1);
+
+long stackrefs_key_compare(void* key1, void* key2);
+
+stackref_hash_value_t *add_stack_ref(VirtualOffset_t pc,int size, int offset);
+stackref_hash_value_t *add_stack_ref_field(stackref_hash_value_t *parent, VirtualOffset_t pc,int size, int offset);
+
+#endif
+
diff --git a/irdb-lib/meds2pdb/strata_defines.h b/irdb-lib/meds2pdb/strata_defines.h
new file mode 100644
index 0000000000000000000000000000000000000000..6b50f8adf5bf9801796af06326d5f4f96f10119d
--- /dev/null
+++ b/irdb-lib/meds2pdb/strata_defines.h
@@ -0,0 +1,31 @@
+/*
+ * strata_defines.h - Declarations for the Strata option package
+ *
+ * Copyright (c) 2000, 2001, 2010 - Zephyr Software
+ *
+ * This file is part of the Strata dynamic code modification infrastructure.
+ * This file may be used and modified for non-commercial purposes as long as 
+ * all copyright, permission, and nonwarranty notices are preserved.  
+ * Redistribution is prohibited without prior written consent from Zephyr 
+ * Software.
+ *
+ * Please contact the authors for restrictions applying to commercial use.
+ *
+ * THIS SOURCE IS PROVIDED "AS IS" AND WITHOUT ANY EXPRESS OR IMPLIED
+ * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
+ * MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ *
+ * Author: Zephyr Software
+ * e-mail: jwd@zephyr-software.com
+ * URL   : http://www.zephyr-software.com/
+ *
+ */
+
+
+#define TRUE (1==1)
+#define FALSE (1==0)
+
+#define TOSTRING(x) STRINGIFY(x)
+#define STRINGIFY(x) #x
+
+
diff --git a/irdb-lib/pebliss/trunk/Makefile b/irdb-lib/pebliss/trunk/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..775475eed83139bab31eb74d5b7d90bdbd14b860
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/Makefile
@@ -0,0 +1,24 @@
+TARGETS = pe_bliss samples_pack tests_pack
+TARGETS_CLEAN = pe_clean samples_clean tests_clean
+
+all: $(TARGETS)
+
+clean: $(TARGETS_CLEAN)
+
+pe_bliss:
+	$(MAKE) PE_DEBUG=$(PE_DEBUG) -C ./pe_lib
+
+samples_pack: pe_bliss
+	$(MAKE) PE_DEBUG=$(PE_DEBUG) -C ./samples
+
+pe_clean:
+	$(MAKE) -C ./pe_lib clean
+
+samples_clean:
+	$(MAKE) -C ./samples clean
+
+tests_pack: pe_bliss
+	$(MAKE) PE_DEBUG=$(PE_DEBUG) -C ./tests
+
+tests_clean:
+	$(MAKE) -C ./tests clean
diff --git a/irdb-lib/pebliss/trunk/pe_bliss_tests_vc10.sln b/irdb-lib/pebliss/trunk/pe_bliss_tests_vc10.sln
new file mode 100644
index 0000000000000000000000000000000000000000..61765d88a46debcd1ef1d052b778135f3372d64b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_bliss_tests_vc10.sln
@@ -0,0 +1,272 @@
+
+Microsoft Visual Studio Solution File, Format Version 11.00
+# Visual Studio 2010
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_checksum", "tests\test_checksum\test_checksum.vcxproj", "{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_entropy", "tests\test_entropy\test_entropy.vcxproj", "{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_rich_data", "tests\test_rich_data\test_rich_data.vcxproj", "{114AC59B-BC28-40DB-8380-67C422D0C81B}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tests_basic", "tests\tests_basic\tests_basic.vcxproj", "{7870A9AC-92BB-423B-BC03-FBF7B46CD338}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tests_utils", "tests\tests_utils\tests_utils.vcxproj", "{50212477-1614-49C9-9791-4AC72025DC76}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_runner", "tests\test_runner\test_runner.vcxproj", "{132DFCC9-13EF-4178-9772-1C467FB296D6}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_imports", "tests\test_imports\test_imports.vcxproj", "{CE1D0620-BC75-456F-914B-3BEBF5444B4C}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_relocations", "tests\test_relocations\test_relocations.vcxproj", "{709B0E41-9792-4A0A-B28B-CBD06CE441B9}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_load_config", "tests\test_load_config\test_load_config.vcxproj", "{FAD361E1-1FD7-4993-BD20-7450026E51CC}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_exception_directory", "tests\test_exception_directory\test_exception_directory.vcxproj", "{B6A37BAA-484D-4175-BEA2-62892A12E8F5}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_tls", "tests\test_tls\test_tls.vcxproj", "{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resources", "tests\test_resources\test_resources.vcxproj", "{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_dotnet", "tests\test_dotnet\test_dotnet.vcxproj", "{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_debug", "tests\test_debug\test_debug.vcxproj", "{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_exports", "tests\test_exports\test_exports.vcxproj", "{82EAF17E-9618-4BD7-AE50-0C325591B585}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_bound_import", "tests\test_bound_import\test_bound_import.vcxproj", "{DA8A8F03-E719-45EF-A376-766A18772FA5}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_viewer", "tests\test_resource_viewer\test_resource_viewer.vcxproj", "{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_manager", "tests\test_resource_manager\test_resource_manager.vcxproj", "{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_bitmap", "tests\test_resource_bitmap\test_resource_bitmap.vcxproj", "{F401B9A2-B8CB-477A-A515-F029D0AA5553}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_icon_cursor", "tests\test_resource_icon_cursor\test_resource_icon_cursor.vcxproj", "{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tests", "Tests", "{6712270F-F056-4512-883A-1756A25D90E1}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_string_table", "tests\test_resource_string_table\test_resource_string_table.vcxproj", "{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_message_table", "tests\test_resource_message_table\test_resource_message_table.vcxproj", "{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_version_info", "tests\test_resource_version_info\test_resource_version_info.vcxproj", "{5C2B081E-5414-437B-86EB-B2695AEDF3F0}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|Win32 = Debug|Win32
+		Debug|x64 = Debug|x64
+		Release|Win32 = Release|Win32
+		Release|x64 = Release|x64
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Debug|Win32.Build.0 = Debug|Win32
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Debug|x64.ActiveCfg = Debug|x64
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Debug|x64.Build.0 = Debug|x64
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Release|Win32.ActiveCfg = Release|Win32
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Release|Win32.Build.0 = Release|Win32
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Release|x64.ActiveCfg = Release|x64
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}.Release|x64.Build.0 = Release|x64
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Debug|Win32.ActiveCfg = Debug|Win32
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Debug|Win32.Build.0 = Debug|Win32
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Debug|x64.ActiveCfg = Debug|x64
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Debug|x64.Build.0 = Debug|x64
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Release|Win32.ActiveCfg = Release|Win32
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Release|Win32.Build.0 = Release|Win32
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Release|x64.ActiveCfg = Release|x64
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}.Release|x64.Build.0 = Release|x64
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Debug|Win32.ActiveCfg = Debug|Win32
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Debug|Win32.Build.0 = Debug|Win32
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Debug|x64.ActiveCfg = Debug|x64
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Debug|x64.Build.0 = Debug|x64
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Release|Win32.ActiveCfg = Release|Win32
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Release|Win32.Build.0 = Release|Win32
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Release|x64.ActiveCfg = Release|x64
+		{114AC59B-BC28-40DB-8380-67C422D0C81B}.Release|x64.Build.0 = Release|x64
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Debug|Win32.ActiveCfg = Debug|Win32
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Debug|Win32.Build.0 = Debug|Win32
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Debug|x64.ActiveCfg = Debug|x64
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Debug|x64.Build.0 = Debug|x64
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Release|Win32.ActiveCfg = Release|Win32
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Release|Win32.Build.0 = Release|Win32
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Release|x64.ActiveCfg = Release|x64
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338}.Release|x64.Build.0 = Release|x64
+		{50212477-1614-49C9-9791-4AC72025DC76}.Debug|Win32.ActiveCfg = Debug|Win32
+		{50212477-1614-49C9-9791-4AC72025DC76}.Debug|Win32.Build.0 = Debug|Win32
+		{50212477-1614-49C9-9791-4AC72025DC76}.Debug|x64.ActiveCfg = Debug|x64
+		{50212477-1614-49C9-9791-4AC72025DC76}.Debug|x64.Build.0 = Debug|x64
+		{50212477-1614-49C9-9791-4AC72025DC76}.Release|Win32.ActiveCfg = Release|Win32
+		{50212477-1614-49C9-9791-4AC72025DC76}.Release|Win32.Build.0 = Release|Win32
+		{50212477-1614-49C9-9791-4AC72025DC76}.Release|x64.ActiveCfg = Release|x64
+		{50212477-1614-49C9-9791-4AC72025DC76}.Release|x64.Build.0 = Release|x64
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Debug|Win32.ActiveCfg = Debug|Win32
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Debug|Win32.Build.0 = Debug|Win32
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Debug|x64.ActiveCfg = Debug|x64
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Debug|x64.Build.0 = Debug|x64
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Release|Win32.ActiveCfg = Release|Win32
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Release|Win32.Build.0 = Release|Win32
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Release|x64.ActiveCfg = Release|x64
+		{132DFCC9-13EF-4178-9772-1C467FB296D6}.Release|x64.Build.0 = Release|x64
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Debug|Win32.Build.0 = Debug|Win32
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Debug|x64.ActiveCfg = Debug|x64
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Debug|x64.Build.0 = Debug|x64
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Release|Win32.ActiveCfg = Release|Win32
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Release|Win32.Build.0 = Release|Win32
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Release|x64.ActiveCfg = Release|x64
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C}.Release|x64.Build.0 = Release|x64
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Debug|Win32.ActiveCfg = Debug|Win32
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Debug|Win32.Build.0 = Debug|Win32
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Debug|x64.ActiveCfg = Debug|x64
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Debug|x64.Build.0 = Debug|x64
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Release|Win32.ActiveCfg = Release|Win32
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Release|Win32.Build.0 = Release|Win32
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Release|x64.ActiveCfg = Release|x64
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9}.Release|x64.Build.0 = Release|x64
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Debug|Win32.ActiveCfg = Debug|Win32
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Debug|Win32.Build.0 = Debug|Win32
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Debug|x64.ActiveCfg = Debug|x64
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Debug|x64.Build.0 = Debug|x64
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Release|Win32.ActiveCfg = Release|Win32
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Release|Win32.Build.0 = Release|Win32
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Release|x64.ActiveCfg = Release|x64
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC}.Release|x64.Build.0 = Release|x64
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Debug|Win32.ActiveCfg = Debug|Win32
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Debug|Win32.Build.0 = Debug|Win32
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Debug|x64.ActiveCfg = Debug|x64
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Debug|x64.Build.0 = Debug|x64
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Release|Win32.ActiveCfg = Release|Win32
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Release|Win32.Build.0 = Release|Win32
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Release|x64.ActiveCfg = Release|x64
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5}.Release|x64.Build.0 = Release|x64
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Debug|Win32.ActiveCfg = Debug|Win32
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Debug|Win32.Build.0 = Debug|Win32
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Debug|x64.ActiveCfg = Debug|x64
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Debug|x64.Build.0 = Debug|x64
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Release|Win32.ActiveCfg = Release|Win32
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Release|Win32.Build.0 = Release|Win32
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Release|x64.ActiveCfg = Release|x64
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}.Release|x64.Build.0 = Release|x64
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Debug|Win32.ActiveCfg = Debug|Win32
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Debug|Win32.Build.0 = Debug|Win32
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Debug|x64.ActiveCfg = Debug|x64
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Debug|x64.Build.0 = Debug|x64
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Release|Win32.ActiveCfg = Release|Win32
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Release|Win32.Build.0 = Release|Win32
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Release|x64.ActiveCfg = Release|x64
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}.Release|x64.Build.0 = Release|x64
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Debug|Win32.ActiveCfg = Debug|Win32
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Debug|Win32.Build.0 = Debug|Win32
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Debug|x64.ActiveCfg = Debug|x64
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Debug|x64.Build.0 = Debug|x64
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Release|Win32.ActiveCfg = Release|Win32
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Release|Win32.Build.0 = Release|Win32
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Release|x64.ActiveCfg = Release|x64
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}.Release|x64.Build.0 = Release|x64
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Debug|Win32.Build.0 = Debug|Win32
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Debug|x64.ActiveCfg = Debug|x64
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Debug|x64.Build.0 = Debug|x64
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Release|Win32.ActiveCfg = Release|Win32
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Release|Win32.Build.0 = Release|Win32
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Release|x64.ActiveCfg = Release|x64
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}.Release|x64.Build.0 = Release|x64
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Debug|Win32.ActiveCfg = Debug|Win32
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Debug|Win32.Build.0 = Debug|Win32
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Debug|x64.ActiveCfg = Debug|x64
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Debug|x64.Build.0 = Debug|x64
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Release|Win32.ActiveCfg = Release|Win32
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Release|Win32.Build.0 = Release|Win32
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Release|x64.ActiveCfg = Release|x64
+		{82EAF17E-9618-4BD7-AE50-0C325591B585}.Release|x64.Build.0 = Release|x64
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Debug|Win32.ActiveCfg = Debug|Win32
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Debug|Win32.Build.0 = Debug|Win32
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Debug|x64.ActiveCfg = Debug|x64
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Debug|x64.Build.0 = Debug|x64
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Release|Win32.ActiveCfg = Release|Win32
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Release|Win32.Build.0 = Release|Win32
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Release|x64.ActiveCfg = Release|x64
+		{DA8A8F03-E719-45EF-A376-766A18772FA5}.Release|x64.Build.0 = Release|x64
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Debug|Win32.Build.0 = Debug|Win32
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Debug|x64.ActiveCfg = Debug|x64
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Debug|x64.Build.0 = Debug|x64
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Release|Win32.ActiveCfg = Release|Win32
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Release|Win32.Build.0 = Release|Win32
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Release|x64.ActiveCfg = Release|x64
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}.Release|x64.Build.0 = Release|x64
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Debug|Win32.ActiveCfg = Debug|Win32
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Debug|Win32.Build.0 = Debug|Win32
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Debug|x64.ActiveCfg = Debug|x64
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Debug|x64.Build.0 = Debug|x64
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Release|Win32.ActiveCfg = Release|Win32
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Release|Win32.Build.0 = Release|Win32
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Release|x64.ActiveCfg = Release|x64
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}.Release|x64.Build.0 = Release|x64
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Debug|Win32.ActiveCfg = Debug|Win32
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Debug|Win32.Build.0 = Debug|Win32
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Debug|x64.ActiveCfg = Debug|x64
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Debug|x64.Build.0 = Debug|x64
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Release|Win32.ActiveCfg = Release|Win32
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Release|Win32.Build.0 = Release|Win32
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Release|x64.ActiveCfg = Release|x64
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553}.Release|x64.Build.0 = Release|x64
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Debug|Win32.ActiveCfg = Debug|Win32
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Debug|Win32.Build.0 = Debug|Win32
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Debug|x64.ActiveCfg = Debug|x64
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Debug|x64.Build.0 = Debug|x64
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Release|Win32.ActiveCfg = Release|Win32
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Release|Win32.Build.0 = Release|Win32
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Release|x64.ActiveCfg = Release|x64
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}.Release|x64.Build.0 = Release|x64
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Debug|Win32.ActiveCfg = Debug|Win32
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Debug|Win32.Build.0 = Debug|Win32
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Debug|x64.ActiveCfg = Debug|x64
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Debug|x64.Build.0 = Debug|x64
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Release|Win32.ActiveCfg = Release|Win32
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Release|Win32.Build.0 = Release|Win32
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Release|x64.ActiveCfg = Release|x64
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}.Release|x64.Build.0 = Release|x64
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Debug|Win32.Build.0 = Debug|Win32
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Debug|x64.ActiveCfg = Debug|x64
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Debug|x64.Build.0 = Debug|x64
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Release|Win32.ActiveCfg = Release|Win32
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Release|Win32.Build.0 = Release|Win32
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Release|x64.ActiveCfg = Release|x64
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}.Release|x64.Build.0 = Release|x64
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Debug|Win32.ActiveCfg = Debug|Win32
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Debug|Win32.Build.0 = Debug|Win32
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Debug|x64.ActiveCfg = Debug|x64
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Debug|x64.Build.0 = Debug|x64
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Release|Win32.ActiveCfg = Release|Win32
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Release|Win32.Build.0 = Release|Win32
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Release|x64.ActiveCfg = Release|x64
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0}.Release|x64.Build.0 = Release|x64
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+	GlobalSection(NestedProjects) = preSolution
+		{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{114AC59B-BC28-40DB-8380-67C422D0C81B} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{7870A9AC-92BB-423B-BC03-FBF7B46CD338} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{50212477-1614-49C9-9791-4AC72025DC76} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{CE1D0620-BC75-456F-914B-3BEBF5444B4C} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{709B0E41-9792-4A0A-B28B-CBD06CE441B9} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{FAD361E1-1FD7-4993-BD20-7450026E51CC} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{B6A37BAA-484D-4175-BEA2-62892A12E8F5} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{82EAF17E-9618-4BD7-AE50-0C325591B585} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{DA8A8F03-E719-45EF-A376-766A18772FA5} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{1FC3537C-EC13-4877-A06C-42DD8B81CBF3} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{F401B9A2-B8CB-477A-A515-F029D0AA5553} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{5E32A144-2F2D-4BB1-BBEF-13BE94414E99} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{6CBACE55-8DDC-4EAE-A23A-DF412265D30C} = {6712270F-F056-4512-883A-1756A25D90E1}
+		{5C2B081E-5414-437B-86EB-B2695AEDF3F0} = {6712270F-F056-4512-883A-1756A25D90E1}
+	EndGlobalSection
+EndGlobal
diff --git a/irdb-lib/pebliss/trunk/pe_bliss_tests_vc9.sln b/irdb-lib/pebliss/trunk/pe_bliss_tests_vc9.sln
new file mode 100644
index 0000000000000000000000000000000000000000..11ccb577a69e14fe599bc9cc344aa3e21a42d26e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_bliss_tests_vc9.sln
@@ -0,0 +1,272 @@
+
+Microsoft Visual Studio Solution File, Format Version 10.00
+# Visual Studio 2008
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_runner", "tests\test_runner\test_runner.vcproj", "{31843E48-DC9A-4887-BD97-328079D78C88}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Tests", "Tests", "{FB42AFF5-C8AA-495F-A397-E073D1A03BDE}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_bound_import", "tests\test_bound_import\test_bound_import.vcproj", "{6EBEAFA6-7489-4026-83D1-CAF67D243119}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_checksum", "tests\test_checksum\test_checksum.vcproj", "{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_dotnet", "tests\test_dotnet\test_dotnet.vcproj", "{094A7331-54E1-4034-BD1E-BE2F974B0142}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_debug", "tests\test_debug\test_debug.vcproj", "{42AC1521-0800-4D81-9363-6EF9362F7A4A}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_entropy", "tests\test_entropy\test_entropy.vcproj", "{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_exception_directory", "tests\test_exception_directory\test_exception_directory.vcproj", "{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_exports", "tests\test_exports\test_exports.vcproj", "{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_imports", "tests\test_imports\test_imports.vcproj", "{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_load_config", "tests\test_load_config\test_load_config.vcproj", "{089E9482-33DD-4C64-84A1-C9B5F10F802A}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_relocations", "tests\test_relocations\test_relocations.vcproj", "{997A89F0-372D-4306-AE4D-7438D93273C3}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_bitmap", "tests\test_resource_bitmap\test_resource_bitmap.vcproj", "{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_icon_cursor", "tests\test_resource_icon_cursor\test_resource_icon_cursor.vcproj", "{1E59538C-2C78-4D35-8639-568890543A4A}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_manager", "tests\test_resource_manager\test_resource_manager.vcproj", "{39E1826B-5436-47D3-9B95-D3C667691461}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_message_table", "tests\test_resource_message_table\test_resource_message_table.vcproj", "{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_string_table", "tests\test_resource_string_table\test_resource_string_table.vcproj", "{C68A466D-0C1B-40BC-9AB1-49B582958524}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_version_info", "tests\test_resource_version_info\test_resource_version_info.vcproj", "{C30B270A-4C93-44A3-AABE-633713D0F1D7}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resource_viewer", "tests\test_resource_viewer\test_resource_viewer.vcproj", "{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_resources", "tests\test_resources\test_resources.vcproj", "{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_rich_data", "tests\test_rich_data\test_rich_data.vcproj", "{1F877026-3D94-41BF-B392-06DFAF67AE34}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "test_tls", "tests\test_tls\test_tls.vcproj", "{63D80BC8-EB14-4698-A391-4A41AC15E8D1}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tests_basic", "tests\tests_basic\tests_basic.vcproj", "{3451AE03-3363-445B-8DA8-94B197563D59}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tests_utils", "tests\tests_utils\tests_utils.vcproj", "{B0478C25-73AD-4085-BA1A-DDF66431EB6E}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|Win32 = Debug|Win32
+		Debug|x64 = Debug|x64
+		Release|Win32 = Release|Win32
+		Release|x64 = Release|x64
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Debug|Win32.ActiveCfg = Debug|Win32
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Debug|Win32.Build.0 = Debug|Win32
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Debug|x64.ActiveCfg = Debug|x64
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Debug|x64.Build.0 = Debug|x64
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Release|Win32.ActiveCfg = Release|Win32
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Release|Win32.Build.0 = Release|Win32
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Release|x64.ActiveCfg = Release|x64
+		{31843E48-DC9A-4887-BD97-328079D78C88}.Release|x64.Build.0 = Release|x64
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Debug|Win32.ActiveCfg = Debug|Win32
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Debug|Win32.Build.0 = Debug|Win32
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Debug|x64.ActiveCfg = Debug|x64
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Debug|x64.Build.0 = Debug|x64
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Release|Win32.ActiveCfg = Release|Win32
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Release|Win32.Build.0 = Release|Win32
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Release|x64.ActiveCfg = Release|x64
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119}.Release|x64.Build.0 = Release|x64
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Debug|Win32.ActiveCfg = Debug|Win32
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Debug|Win32.Build.0 = Debug|Win32
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Debug|x64.ActiveCfg = Debug|x64
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Debug|x64.Build.0 = Debug|x64
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Release|Win32.ActiveCfg = Release|Win32
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Release|Win32.Build.0 = Release|Win32
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Release|x64.ActiveCfg = Release|x64
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}.Release|x64.Build.0 = Release|x64
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Debug|Win32.ActiveCfg = Debug|Win32
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Debug|Win32.Build.0 = Debug|Win32
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Debug|x64.ActiveCfg = Debug|x64
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Debug|x64.Build.0 = Debug|x64
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Release|Win32.ActiveCfg = Release|Win32
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Release|Win32.Build.0 = Release|Win32
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Release|x64.ActiveCfg = Release|x64
+		{094A7331-54E1-4034-BD1E-BE2F974B0142}.Release|x64.Build.0 = Release|x64
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Debug|Win32.Build.0 = Debug|Win32
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Debug|x64.ActiveCfg = Debug|x64
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Debug|x64.Build.0 = Debug|x64
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Release|Win32.ActiveCfg = Release|Win32
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Release|Win32.Build.0 = Release|Win32
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Release|x64.ActiveCfg = Release|x64
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A}.Release|x64.Build.0 = Release|x64
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Debug|Win32.ActiveCfg = Debug|Win32
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Debug|Win32.Build.0 = Debug|Win32
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Debug|x64.ActiveCfg = Debug|x64
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Debug|x64.Build.0 = Debug|x64
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Release|Win32.ActiveCfg = Release|Win32
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Release|Win32.Build.0 = Release|Win32
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Release|x64.ActiveCfg = Release|x64
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}.Release|x64.Build.0 = Release|x64
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Debug|Win32.Build.0 = Debug|Win32
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Debug|x64.ActiveCfg = Debug|x64
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Debug|x64.Build.0 = Debug|x64
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Release|Win32.ActiveCfg = Release|Win32
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Release|Win32.Build.0 = Release|Win32
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Release|x64.ActiveCfg = Release|x64
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}.Release|x64.Build.0 = Release|x64
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Debug|Win32.ActiveCfg = Debug|Win32
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Debug|Win32.Build.0 = Debug|Win32
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Debug|x64.ActiveCfg = Debug|x64
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Debug|x64.Build.0 = Debug|x64
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Release|Win32.ActiveCfg = Release|Win32
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Release|Win32.Build.0 = Release|Win32
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Release|x64.ActiveCfg = Release|x64
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}.Release|x64.Build.0 = Release|x64
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Debug|Win32.ActiveCfg = Debug|Win32
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Debug|Win32.Build.0 = Debug|Win32
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Debug|x64.ActiveCfg = Debug|x64
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Debug|x64.Build.0 = Debug|x64
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Release|Win32.ActiveCfg = Release|Win32
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Release|Win32.Build.0 = Release|Win32
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Release|x64.ActiveCfg = Release|x64
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}.Release|x64.Build.0 = Release|x64
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Debug|Win32.Build.0 = Debug|Win32
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Debug|x64.ActiveCfg = Debug|x64
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Debug|x64.Build.0 = Debug|x64
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Release|Win32.ActiveCfg = Release|Win32
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Release|Win32.Build.0 = Release|Win32
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Release|x64.ActiveCfg = Release|x64
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A}.Release|x64.Build.0 = Release|x64
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Debug|Win32.ActiveCfg = Debug|Win32
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Debug|Win32.Build.0 = Debug|Win32
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Debug|x64.ActiveCfg = Debug|x64
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Debug|x64.Build.0 = Debug|x64
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Release|Win32.ActiveCfg = Release|Win32
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Release|Win32.Build.0 = Release|Win32
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Release|x64.ActiveCfg = Release|x64
+		{997A89F0-372D-4306-AE4D-7438D93273C3}.Release|x64.Build.0 = Release|x64
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Debug|Win32.Build.0 = Debug|Win32
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Debug|x64.ActiveCfg = Debug|x64
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Debug|x64.Build.0 = Debug|x64
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Release|Win32.ActiveCfg = Release|Win32
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Release|Win32.Build.0 = Release|Win32
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Release|x64.ActiveCfg = Release|x64
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}.Release|x64.Build.0 = Release|x64
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Debug|Win32.Build.0 = Debug|Win32
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Debug|x64.ActiveCfg = Debug|x64
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Debug|x64.Build.0 = Debug|x64
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Release|Win32.ActiveCfg = Release|Win32
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Release|Win32.Build.0 = Release|Win32
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Release|x64.ActiveCfg = Release|x64
+		{1E59538C-2C78-4D35-8639-568890543A4A}.Release|x64.Build.0 = Release|x64
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Debug|Win32.ActiveCfg = Debug|Win32
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Debug|Win32.Build.0 = Debug|Win32
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Debug|x64.ActiveCfg = Debug|x64
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Debug|x64.Build.0 = Debug|x64
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Release|Win32.ActiveCfg = Release|Win32
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Release|Win32.Build.0 = Release|Win32
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Release|x64.ActiveCfg = Release|x64
+		{39E1826B-5436-47D3-9B95-D3C667691461}.Release|x64.Build.0 = Release|x64
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Debug|Win32.ActiveCfg = Debug|Win32
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Debug|Win32.Build.0 = Debug|Win32
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Debug|x64.ActiveCfg = Debug|x64
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Debug|x64.Build.0 = Debug|x64
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Release|Win32.ActiveCfg = Release|Win32
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Release|Win32.Build.0 = Release|Win32
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Release|x64.ActiveCfg = Release|x64
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}.Release|x64.Build.0 = Release|x64
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Debug|Win32.ActiveCfg = Debug|Win32
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Debug|Win32.Build.0 = Debug|Win32
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Debug|x64.ActiveCfg = Debug|x64
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Debug|x64.Build.0 = Debug|x64
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Release|Win32.ActiveCfg = Release|Win32
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Release|Win32.Build.0 = Release|Win32
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Release|x64.ActiveCfg = Release|x64
+		{C68A466D-0C1B-40BC-9AB1-49B582958524}.Release|x64.Build.0 = Release|x64
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Debug|Win32.ActiveCfg = Debug|Win32
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Debug|Win32.Build.0 = Debug|Win32
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Debug|x64.ActiveCfg = Debug|x64
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Debug|x64.Build.0 = Debug|x64
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Release|Win32.ActiveCfg = Release|Win32
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Release|Win32.Build.0 = Release|Win32
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Release|x64.ActiveCfg = Release|x64
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7}.Release|x64.Build.0 = Release|x64
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Debug|Win32.ActiveCfg = Debug|Win32
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Debug|Win32.Build.0 = Debug|Win32
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Debug|x64.ActiveCfg = Debug|x64
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Debug|x64.Build.0 = Debug|x64
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Release|Win32.ActiveCfg = Release|Win32
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Release|Win32.Build.0 = Release|Win32
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Release|x64.ActiveCfg = Release|x64
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}.Release|x64.Build.0 = Release|x64
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Debug|Win32.Build.0 = Debug|Win32
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Debug|x64.ActiveCfg = Debug|x64
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Debug|x64.Build.0 = Debug|x64
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Release|Win32.ActiveCfg = Release|Win32
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Release|Win32.Build.0 = Release|Win32
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Release|x64.ActiveCfg = Release|x64
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}.Release|x64.Build.0 = Release|x64
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Debug|Win32.Build.0 = Debug|Win32
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Debug|x64.ActiveCfg = Debug|x64
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Debug|x64.Build.0 = Debug|x64
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Release|Win32.ActiveCfg = Release|Win32
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Release|Win32.Build.0 = Release|Win32
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Release|x64.ActiveCfg = Release|x64
+		{1F877026-3D94-41BF-B392-06DFAF67AE34}.Release|x64.Build.0 = Release|x64
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Debug|Win32.ActiveCfg = Debug|Win32
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Debug|Win32.Build.0 = Debug|Win32
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Debug|x64.ActiveCfg = Debug|x64
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Debug|x64.Build.0 = Debug|x64
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Release|Win32.ActiveCfg = Release|Win32
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Release|Win32.Build.0 = Release|Win32
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Release|x64.ActiveCfg = Release|x64
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1}.Release|x64.Build.0 = Release|x64
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Debug|Win32.ActiveCfg = Debug|Win32
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Debug|Win32.Build.0 = Debug|Win32
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Debug|x64.ActiveCfg = Debug|x64
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Debug|x64.Build.0 = Debug|x64
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Release|Win32.ActiveCfg = Release|Win32
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Release|Win32.Build.0 = Release|Win32
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Release|x64.ActiveCfg = Release|x64
+		{3451AE03-3363-445B-8DA8-94B197563D59}.Release|x64.Build.0 = Release|x64
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Debug|Win32.ActiveCfg = Debug|Win32
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Debug|Win32.Build.0 = Debug|Win32
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Debug|x64.ActiveCfg = Debug|x64
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Debug|x64.Build.0 = Debug|x64
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Release|Win32.ActiveCfg = Release|Win32
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Release|Win32.Build.0 = Release|Win32
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Release|x64.ActiveCfg = Release|x64
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E}.Release|x64.Build.0 = Release|x64
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+	GlobalSection(NestedProjects) = preSolution
+		{6EBEAFA6-7489-4026-83D1-CAF67D243119} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{094A7331-54E1-4034-BD1E-BE2F974B0142} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{42AC1521-0800-4D81-9363-6EF9362F7A4A} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{1C36ED94-CBE5-4107-83B6-9C37F3A4041C} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{BD969F96-E5A5-47B2-B5EF-B7999A441CE5} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{089E9482-33DD-4C64-84A1-C9B5F10F802A} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{997A89F0-372D-4306-AE4D-7438D93273C3} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{1B337DC2-628E-4DA4-8C0F-A6880289C6E2} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{1E59538C-2C78-4D35-8639-568890543A4A} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{39E1826B-5436-47D3-9B95-D3C667691461} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{57EFEFC9-E2D9-418E-9F05-3FD0D9921251} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{C68A466D-0C1B-40BC-9AB1-49B582958524} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{C30B270A-4C93-44A3-AABE-633713D0F1D7} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{7E3867A9-59BC-4441-A74E-F4ABFFEE231C} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{1F877026-3D94-41BF-B392-06DFAF67AE34} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{63D80BC8-EB14-4698-A391-4A41AC15E8D1} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{3451AE03-3363-445B-8DA8-94B197563D59} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+		{B0478C25-73AD-4085-BA1A-DDF66431EB6E} = {FB42AFF5-C8AA-495F-A397-E073D1A03BDE}
+	EndGlobalSection
+EndGlobal
diff --git a/irdb-lib/pebliss/trunk/pe_bliss_vc10.sln b/irdb-lib/pebliss/trunk/pe_bliss_vc10.sln
new file mode 100644
index 0000000000000000000000000000000000000000..587aa18c4d31ae985090a5bc34263d5dbf6153a3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_bliss_vc10.sln
@@ -0,0 +1,417 @@
+
+Microsoft Visual Studio Solution File, Format Version 11.00
+# Visual Studio 2010
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_bliss", "pe_lib\pe_lib.vcxproj", "{1461F543-D1FA-4E4C-B6D7-0F879F566035}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "View PE information", "View PE information", "{49B3F007-A569-40AE-8FB4-A2AE0347F479}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "PE Library", "PE Library", "{9554CAF4-678B-4E42-B886-0F9771FD2B61}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Edit PE files", "Edit PE files", "{53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "address_convertions", "samples\address_convertions\address_convertions.vcxproj", "{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "basic_info_viewer", "samples\basic_info_viewer\basic_info_viewer.vcxproj", "{71707667-1A10-4B53-AC02-E4AD898AC6E7}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "bound_import_reader", "samples\bound_import_reader\bound_import_reader.vcxproj", "{EFC31F33-D5E4-4356-A892-18CADABCFCCF}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "debug_info_reader", "samples\debug_info_reader\debug_info_reader.vcxproj", "{332A1418-E89B-4658-9F7F-8D219ED776EA}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "entropy_calculator", "samples\entropy_calculator\entropy_calculator.vcxproj", "{48879460-0DF8-491E-BD1D-A489C8D92746}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "exception_dir_reader", "samples\exception_dir_reader\exception_dir_reader.vcxproj", "{EFAF41AB-C77D-4819-996E-4F6C305553A5}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "exports_reader", "samples\exports_reader\exports_reader.vcxproj", "{32ABD41F-7BCE-43E0-853E-21E16260EDB7}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "imports_reader", "samples\imports_reader\imports_reader.vcxproj", "{752670B7-53AA-46CF-B3C5-D3FABBDC027D}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_config_reader", "samples\pe_config_reader\pe_config_reader.vcxproj", "{4F642892-D07F-4A96-82E4-36E2966D222D}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_sections_reader", "samples\pe_sections_reader\pe_sections_reader.vcxproj", "{F154B72B-22DD-493A-B5D5-CDCD8914DA28}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "relocations_reader", "samples\relocations_reader\relocations_reader.vcxproj", "{A188C743-EA65-4D18-8964-18EAE61ACAC2}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "resource_viewer", "samples\resource_viewer\resource_viewer.vcxproj", "{BC2D8697-73C1-46B9-AC1C-7777D1A71609}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "rich_overlay_stub_reader", "samples\rich_overlay_stub_reader\rich_overlay_stub_reader.vcxproj", "{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "sections_and_addresses", "samples\sections_and_addresses\sections_and_addresses.vcxproj", "{99F41F8F-44DB-410E-9883-A6A16E903DF8}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tls_reader", "samples\tls_reader\tls_reader.vcxproj", "{CFB9A225-E2E5-43BC-898A-6D52357E7F92}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "basic_dotnet_viewer", "samples\basic_dotnet_viewer\basic_dotnet_viewer.vcxproj", "{5E2C4403-4C8B-4773-89A6-61547756ABDC}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "section_adder", "samples\section_adder\section_adder.vcxproj", "{93ABC577-1018-48C2-95C6-39B0B26DD3B0}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_rebaser", "samples\pe_rebaser\pe_rebaser.vcxproj", "{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_stripper", "samples\pe_stripper\pe_stripper.vcxproj", "{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_realigner", "samples\pe_realigner\pe_realigner.vcxproj", "{F40CE9C6-5E3F-445A-8EA4-ED819E608024}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "import_adder", "samples\import_adder\import_adder.vcxproj", "{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "export_adder", "samples\export_adder\export_adder.vcxproj", "{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "relocation_adder", "samples\relocation_adder\relocation_adder.vcxproj", "{7375047B-90D7-4564-BA84-7E5C638C7CCE}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tls_editor", "samples\tls_editor\tls_editor.vcxproj", "{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "resource_editor", "samples\resource_editor\resource_editor.vcxproj", "{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "image_config_editor", "samples\image_config_editor\image_config_editor.vcxproj", "{48B99169-44E6-41E5-A681-78243B885E86}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "full_pe_rebuilder", "samples\full_pe_rebuilder\full_pe_rebuilder.vcxproj", "{D7F6EE93-F88A-4B66-8761-87EC844E20C5}"
+	ProjectSection(ProjectDependencies) = postProject
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {1461F543-D1FA-4E4C-B6D7-0F879F566035}
+	EndProjectSection
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Samples", "Samples", "{65326322-DFB0-46BF-80A6-84B8A7C9628D}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|Win32 = Debug|Win32
+		Debug|x64 = Debug|x64
+		Release|Win32 = Release|Win32
+		Release|x64 = Release|x64
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Debug|Win32.Build.0 = Debug|Win32
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Debug|x64.ActiveCfg = Debug|x64
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Debug|x64.Build.0 = Debug|x64
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Release|Win32.ActiveCfg = Release|Win32
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Release|Win32.Build.0 = Release|Win32
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Release|x64.ActiveCfg = Release|x64
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035}.Release|x64.Build.0 = Release|x64
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Debug|Win32.ActiveCfg = Debug|Win32
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Debug|Win32.Build.0 = Debug|Win32
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Debug|x64.ActiveCfg = Debug|x64
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Debug|x64.Build.0 = Debug|x64
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Release|Win32.ActiveCfg = Release|Win32
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Release|Win32.Build.0 = Release|Win32
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Release|x64.ActiveCfg = Release|x64
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}.Release|x64.Build.0 = Release|x64
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Debug|Win32.ActiveCfg = Debug|Win32
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Debug|Win32.Build.0 = Debug|Win32
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Debug|x64.ActiveCfg = Debug|x64
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Debug|x64.Build.0 = Debug|x64
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Release|Win32.ActiveCfg = Release|Win32
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Release|Win32.Build.0 = Release|Win32
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Release|x64.ActiveCfg = Release|x64
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7}.Release|x64.Build.0 = Release|x64
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Debug|Win32.ActiveCfg = Debug|Win32
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Debug|Win32.Build.0 = Debug|Win32
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Debug|x64.ActiveCfg = Debug|x64
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Debug|x64.Build.0 = Debug|x64
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Release|Win32.ActiveCfg = Release|Win32
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Release|Win32.Build.0 = Release|Win32
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Release|x64.ActiveCfg = Release|x64
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF}.Release|x64.Build.0 = Release|x64
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Debug|Win32.ActiveCfg = Debug|Win32
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Debug|Win32.Build.0 = Debug|Win32
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Debug|x64.ActiveCfg = Debug|x64
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Debug|x64.Build.0 = Debug|x64
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Release|Win32.ActiveCfg = Release|Win32
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Release|Win32.Build.0 = Release|Win32
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Release|x64.ActiveCfg = Release|x64
+		{332A1418-E89B-4658-9F7F-8D219ED776EA}.Release|x64.Build.0 = Release|x64
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Debug|Win32.ActiveCfg = Debug|Win32
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Debug|Win32.Build.0 = Debug|Win32
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Debug|x64.ActiveCfg = Debug|x64
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Debug|x64.Build.0 = Debug|x64
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Release|Win32.ActiveCfg = Release|Win32
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Release|Win32.Build.0 = Release|Win32
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Release|x64.ActiveCfg = Release|x64
+		{48879460-0DF8-491E-BD1D-A489C8D92746}.Release|x64.Build.0 = Release|x64
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Debug|Win32.ActiveCfg = Debug|Win32
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Debug|Win32.Build.0 = Debug|Win32
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Debug|x64.ActiveCfg = Debug|x64
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Debug|x64.Build.0 = Debug|x64
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Release|Win32.ActiveCfg = Release|Win32
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Release|Win32.Build.0 = Release|Win32
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Release|x64.ActiveCfg = Release|x64
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5}.Release|x64.Build.0 = Release|x64
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Debug|Win32.ActiveCfg = Debug|Win32
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Debug|Win32.Build.0 = Debug|Win32
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Debug|x64.ActiveCfg = Debug|x64
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Debug|x64.Build.0 = Debug|x64
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Release|Win32.ActiveCfg = Release|Win32
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Release|Win32.Build.0 = Release|Win32
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Release|x64.ActiveCfg = Release|x64
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7}.Release|x64.Build.0 = Release|x64
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Debug|Win32.ActiveCfg = Debug|Win32
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Debug|Win32.Build.0 = Debug|Win32
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Debug|x64.ActiveCfg = Debug|x64
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Debug|x64.Build.0 = Debug|x64
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Release|Win32.ActiveCfg = Release|Win32
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Release|Win32.Build.0 = Release|Win32
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Release|x64.ActiveCfg = Release|x64
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D}.Release|x64.Build.0 = Release|x64
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Debug|Win32.ActiveCfg = Debug|Win32
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Debug|Win32.Build.0 = Debug|Win32
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Debug|x64.ActiveCfg = Debug|x64
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Debug|x64.Build.0 = Debug|x64
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Release|Win32.ActiveCfg = Release|Win32
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Release|Win32.Build.0 = Release|Win32
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Release|x64.ActiveCfg = Release|x64
+		{4F642892-D07F-4A96-82E4-36E2966D222D}.Release|x64.Build.0 = Release|x64
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Debug|Win32.ActiveCfg = Debug|Win32
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Debug|Win32.Build.0 = Debug|Win32
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Debug|x64.ActiveCfg = Debug|x64
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Debug|x64.Build.0 = Debug|x64
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Release|Win32.ActiveCfg = Release|Win32
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Release|Win32.Build.0 = Release|Win32
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Release|x64.ActiveCfg = Release|x64
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28}.Release|x64.Build.0 = Release|x64
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Debug|Win32.ActiveCfg = Debug|Win32
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Debug|Win32.Build.0 = Debug|Win32
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Debug|x64.ActiveCfg = Debug|x64
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Debug|x64.Build.0 = Debug|x64
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Release|Win32.ActiveCfg = Release|Win32
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Release|Win32.Build.0 = Release|Win32
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Release|x64.ActiveCfg = Release|x64
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2}.Release|x64.Build.0 = Release|x64
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Debug|Win32.ActiveCfg = Debug|Win32
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Debug|Win32.Build.0 = Debug|Win32
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Debug|x64.ActiveCfg = Debug|x64
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Debug|x64.Build.0 = Debug|x64
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Release|Win32.ActiveCfg = Release|Win32
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Release|Win32.Build.0 = Release|Win32
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Release|x64.ActiveCfg = Release|x64
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609}.Release|x64.Build.0 = Release|x64
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Debug|Win32.ActiveCfg = Debug|Win32
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Debug|Win32.Build.0 = Debug|Win32
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Debug|x64.ActiveCfg = Debug|x64
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Debug|x64.Build.0 = Debug|x64
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Release|Win32.ActiveCfg = Release|Win32
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Release|Win32.Build.0 = Release|Win32
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Release|x64.ActiveCfg = Release|x64
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}.Release|x64.Build.0 = Release|x64
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Debug|Win32.ActiveCfg = Debug|Win32
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Debug|Win32.Build.0 = Debug|Win32
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Debug|x64.ActiveCfg = Debug|x64
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Debug|x64.Build.0 = Debug|x64
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Release|Win32.ActiveCfg = Release|Win32
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Release|Win32.Build.0 = Release|Win32
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Release|x64.ActiveCfg = Release|x64
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8}.Release|x64.Build.0 = Release|x64
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Debug|Win32.ActiveCfg = Debug|Win32
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Debug|Win32.Build.0 = Debug|Win32
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Debug|x64.ActiveCfg = Debug|x64
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Debug|x64.Build.0 = Debug|x64
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Release|Win32.ActiveCfg = Release|Win32
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Release|Win32.Build.0 = Release|Win32
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Release|x64.ActiveCfg = Release|x64
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92}.Release|x64.Build.0 = Release|x64
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Debug|Win32.ActiveCfg = Debug|Win32
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Debug|Win32.Build.0 = Debug|Win32
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Debug|x64.ActiveCfg = Debug|x64
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Debug|x64.Build.0 = Debug|x64
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Release|Win32.ActiveCfg = Release|Win32
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Release|Win32.Build.0 = Release|Win32
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Release|x64.ActiveCfg = Release|x64
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC}.Release|x64.Build.0 = Release|x64
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Debug|Win32.ActiveCfg = Debug|Win32
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Debug|Win32.Build.0 = Debug|Win32
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Debug|x64.ActiveCfg = Debug|x64
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Debug|x64.Build.0 = Debug|x64
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Release|Win32.ActiveCfg = Release|Win32
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Release|Win32.Build.0 = Release|Win32
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Release|x64.ActiveCfg = Release|x64
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0}.Release|x64.Build.0 = Release|x64
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Debug|Win32.ActiveCfg = Debug|Win32
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Debug|Win32.Build.0 = Debug|Win32
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Debug|x64.ActiveCfg = Debug|x64
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Debug|x64.Build.0 = Debug|x64
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Release|Win32.ActiveCfg = Release|Win32
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Release|Win32.Build.0 = Release|Win32
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Release|x64.ActiveCfg = Release|x64
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}.Release|x64.Build.0 = Release|x64
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Debug|Win32.ActiveCfg = Debug|Win32
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Debug|Win32.Build.0 = Debug|Win32
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Debug|x64.ActiveCfg = Debug|x64
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Debug|x64.Build.0 = Debug|x64
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Release|Win32.ActiveCfg = Release|Win32
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Release|Win32.Build.0 = Release|Win32
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Release|x64.ActiveCfg = Release|x64
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}.Release|x64.Build.0 = Release|x64
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Debug|Win32.ActiveCfg = Debug|Win32
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Debug|Win32.Build.0 = Debug|Win32
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Debug|x64.ActiveCfg = Debug|x64
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Debug|x64.Build.0 = Debug|x64
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Release|Win32.ActiveCfg = Release|Win32
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Release|Win32.Build.0 = Release|Win32
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Release|x64.ActiveCfg = Release|x64
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024}.Release|x64.Build.0 = Release|x64
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Debug|Win32.ActiveCfg = Debug|Win32
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Debug|Win32.Build.0 = Debug|Win32
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Debug|x64.ActiveCfg = Debug|x64
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Debug|x64.Build.0 = Debug|x64
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Release|Win32.ActiveCfg = Release|Win32
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Release|Win32.Build.0 = Release|Win32
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Release|x64.ActiveCfg = Release|x64
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}.Release|x64.Build.0 = Release|x64
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Debug|Win32.ActiveCfg = Debug|Win32
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Debug|Win32.Build.0 = Debug|Win32
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Debug|x64.ActiveCfg = Debug|x64
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Debug|x64.Build.0 = Debug|x64
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Release|Win32.ActiveCfg = Release|Win32
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Release|Win32.Build.0 = Release|Win32
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Release|x64.ActiveCfg = Release|x64
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}.Release|x64.Build.0 = Release|x64
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Debug|Win32.ActiveCfg = Debug|Win32
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Debug|Win32.Build.0 = Debug|Win32
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Debug|x64.ActiveCfg = Debug|x64
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Debug|x64.Build.0 = Debug|x64
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Release|Win32.ActiveCfg = Release|Win32
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Release|Win32.Build.0 = Release|Win32
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Release|x64.ActiveCfg = Release|x64
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE}.Release|x64.Build.0 = Release|x64
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Debug|Win32.Build.0 = Debug|Win32
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Debug|x64.ActiveCfg = Debug|x64
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Debug|x64.Build.0 = Debug|x64
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Release|Win32.ActiveCfg = Release|Win32
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Release|Win32.Build.0 = Release|Win32
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Release|x64.ActiveCfg = Release|x64
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}.Release|x64.Build.0 = Release|x64
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Debug|Win32.ActiveCfg = Debug|Win32
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Debug|Win32.Build.0 = Debug|Win32
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Debug|x64.ActiveCfg = Debug|x64
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Debug|x64.Build.0 = Debug|x64
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Release|Win32.ActiveCfg = Release|Win32
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Release|Win32.Build.0 = Release|Win32
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Release|x64.ActiveCfg = Release|x64
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}.Release|x64.Build.0 = Release|x64
+		{48B99169-44E6-41E5-A681-78243B885E86}.Debug|Win32.ActiveCfg = Debug|Win32
+		{48B99169-44E6-41E5-A681-78243B885E86}.Debug|Win32.Build.0 = Debug|Win32
+		{48B99169-44E6-41E5-A681-78243B885E86}.Debug|x64.ActiveCfg = Debug|x64
+		{48B99169-44E6-41E5-A681-78243B885E86}.Debug|x64.Build.0 = Debug|x64
+		{48B99169-44E6-41E5-A681-78243B885E86}.Release|Win32.ActiveCfg = Release|Win32
+		{48B99169-44E6-41E5-A681-78243B885E86}.Release|Win32.Build.0 = Release|Win32
+		{48B99169-44E6-41E5-A681-78243B885E86}.Release|x64.ActiveCfg = Release|x64
+		{48B99169-44E6-41E5-A681-78243B885E86}.Release|x64.Build.0 = Release|x64
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Debug|Win32.ActiveCfg = Debug|Win32
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Debug|Win32.Build.0 = Debug|Win32
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Debug|x64.ActiveCfg = Debug|x64
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Debug|x64.Build.0 = Debug|x64
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Release|Win32.ActiveCfg = Release|Win32
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Release|Win32.Build.0 = Release|Win32
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Release|x64.ActiveCfg = Release|x64
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5}.Release|x64.Build.0 = Release|x64
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+	GlobalSection(NestedProjects) = preSolution
+		{1461F543-D1FA-4E4C-B6D7-0F879F566035} = {9554CAF4-678B-4E42-B886-0F9771FD2B61}
+		{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{71707667-1A10-4B53-AC02-E4AD898AC6E7} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{EFC31F33-D5E4-4356-A892-18CADABCFCCF} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{332A1418-E89B-4658-9F7F-8D219ED776EA} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{48879460-0DF8-491E-BD1D-A489C8D92746} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{EFAF41AB-C77D-4819-996E-4F6C305553A5} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{32ABD41F-7BCE-43E0-853E-21E16260EDB7} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{752670B7-53AA-46CF-B3C5-D3FABBDC027D} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{4F642892-D07F-4A96-82E4-36E2966D222D} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{F154B72B-22DD-493A-B5D5-CDCD8914DA28} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{A188C743-EA65-4D18-8964-18EAE61ACAC2} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{BC2D8697-73C1-46B9-AC1C-7777D1A71609} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{99F41F8F-44DB-410E-9883-A6A16E903DF8} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{CFB9A225-E2E5-43BC-898A-6D52357E7F92} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{5E2C4403-4C8B-4773-89A6-61547756ABDC} = {49B3F007-A569-40AE-8FB4-A2AE0347F479}
+		{93ABC577-1018-48C2-95C6-39B0B26DD3B0} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{46FD39E7-B16C-4F73-B2F0-F1B570464C6E} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{F40CE9C6-5E3F-445A-8EA4-ED819E608024} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{17C01A93-C7F0-49EB-A9A0-81F5E06779C3} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{7375047B-90D7-4564-BA84-7E5C638C7CCE} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{B88455A6-C93A-4F17-93A5-FC84B70F9CFE} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{48B99169-44E6-41E5-A681-78243B885E86} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{D7F6EE93-F88A-4B66-8761-87EC844E20C5} = {53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036}
+		{53A03406-AEFB-4ABA-8DD1-5AE9B8DFB036} = {65326322-DFB0-46BF-80A6-84B8A7C9628D}
+		{49B3F007-A569-40AE-8FB4-A2AE0347F479} = {65326322-DFB0-46BF-80A6-84B8A7C9628D}
+	EndGlobalSection
+EndGlobal
diff --git a/irdb-lib/pebliss/trunk/pe_bliss_vc9.sln b/irdb-lib/pebliss/trunk/pe_bliss_vc9.sln
new file mode 100644
index 0000000000000000000000000000000000000000..d6c04b4569ff8fcf11d36c2162daa39cdee8e1ea
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_bliss_vc9.sln
@@ -0,0 +1,417 @@
+
+Microsoft Visual Studio Solution File, Format Version 10.00
+# Visual Studio 2008
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_lib", "pe_lib\pe_lib.vcproj", "{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "PE Library", "PE Library", "{20B98358-3862-4D16-985F-ECE9DE5D9FEB}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "View PE information", "View PE information", "{25A7C026-702D-48A4-A1EC-81DE78F0664E}"
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Edit PE files", "Edit PE files", "{0CF51D6D-1F80-4D2C-95BE-566641BD1F71}"
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "address_convertions", "samples\address_convertions\address_convertions.vcproj", "{642392B3-C763-44C8-91F4-EA90C3651608}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "basic_dotnet_viewer", "samples\basic_dotnet_viewer\basic_dotnet_viewer.vcproj", "{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "basic_info_viewer", "samples\basic_info_viewer\basic_info_viewer.vcproj", "{7AF45D7B-8341-42CF-B382-B67E1399D8B1}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "bound_import_reader", "samples\bound_import_reader\bound_import_reader.vcproj", "{65229ACC-5C9B-429C-B9DA-4710697637EB}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "debug_info_reader", "samples\debug_info_reader\debug_info_reader.vcproj", "{218033A7-A6D0-45B4-88F6-F4FF5DD25207}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "entropy_calculator", "samples\entropy_calculator\entropy_calculator.vcproj", "{111344DB-1F0B-460E-91DD-9DD36D2238A4}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "exception_dir_reader", "samples\exception_dir_reader\exception_dir_reader.vcproj", "{D8E2714A-11A7-478D-A966-EF6968FFB766}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "export_adder", "samples\export_adder\export_adder.vcproj", "{4459EB9F-0332-46C4-BF60-6CECA73C7D17}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "exports_reader", "samples\exports_reader\exports_reader.vcproj", "{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "import_adder", "samples\import_adder\import_adder.vcproj", "{5303D6F1-D667-4E92-A501-8B396252156F}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "imports_reader", "samples\imports_reader\imports_reader.vcproj", "{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_config_reader", "samples\pe_config_reader\pe_config_reader.vcproj", "{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_realigner", "samples\pe_realigner\pe_realigner.vcproj", "{36EB9E03-E155-4487-AB1B-0B1B862B0155}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_rebaser", "samples\pe_rebaser\pe_rebaser.vcproj", "{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_sections_reader", "samples\pe_sections_reader\pe_sections_reader.vcproj", "{0A06D231-FC40-4EC9-B0FC-F0D08270384E}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "pe_stripper", "samples\pe_stripper\pe_stripper.vcproj", "{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "relocation_adder", "samples\relocation_adder\relocation_adder.vcproj", "{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "relocations_reader", "samples\relocations_reader\relocations_reader.vcproj", "{3EDCB092-C785-41EB-8A83-C5B37A2FF310}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "resource_editor", "samples\resource_editor\resource_editor.vcproj", "{B0D287DB-451D-4005-9CE3-185D7602F0B7}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "resource_viewer", "samples\resource_viewer\resource_viewer.vcproj", "{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "rich_overlay_stub_reader", "samples\rich_overlay_stub_reader\rich_overlay_stub_reader.vcproj", "{33FF435B-A3CF-441E-964E-A7DA8735E7B1}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "section_adder", "samples\section_adder\section_adder.vcproj", "{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "sections_and_addresses", "samples\sections_and_addresses\sections_and_addresses.vcproj", "{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tls_editor", "samples\tls_editor\tls_editor.vcproj", "{781B56DF-15CE-4CBA-A008-0403029E558A}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "tls_reader", "samples\tls_reader\tls_reader.vcproj", "{BA36739B-F101-4C91-928D-678AB9521A22}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "image_config_editor", "samples\image_config_editor\image_config_editor.vcproj", "{22788F46-AB6B-4278-B1C0-ED220AE85F4A}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "full_pe_rebuilder", "samples\full_pe_rebuilder\full_pe_rebuilder.vcproj", "{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}"
+	ProjectSection(ProjectDependencies) = postProject
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}
+	EndProjectSection
+EndProject
+Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Samples", "Samples", "{9191A7C3-3B0A-45A5-99A2-72D1903AA7B7}"
+EndProject
+Global
+	GlobalSection(SolutionConfigurationPlatforms) = preSolution
+		Debug|Win32 = Debug|Win32
+		Debug|x64 = Debug|x64
+		Release|Win32 = Release|Win32
+		Release|x64 = Release|x64
+	EndGlobalSection
+	GlobalSection(ProjectConfigurationPlatforms) = postSolution
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Debug|Win32.Build.0 = Debug|Win32
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Debug|x64.ActiveCfg = Debug|x64
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Debug|x64.Build.0 = Debug|x64
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Release|Win32.ActiveCfg = Release|Win32
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Release|Win32.Build.0 = Release|Win32
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Release|x64.ActiveCfg = Release|x64
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}.Release|x64.Build.0 = Release|x64
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Debug|Win32.ActiveCfg = Debug|Win32
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Debug|Win32.Build.0 = Debug|Win32
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Debug|x64.ActiveCfg = Debug|x64
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Debug|x64.Build.0 = Debug|x64
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Release|Win32.ActiveCfg = Release|Win32
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Release|Win32.Build.0 = Release|Win32
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Release|x64.ActiveCfg = Release|x64
+		{642392B3-C763-44C8-91F4-EA90C3651608}.Release|x64.Build.0 = Release|x64
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Debug|Win32.ActiveCfg = Debug|Win32
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Debug|Win32.Build.0 = Debug|Win32
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Debug|x64.ActiveCfg = Debug|x64
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Debug|x64.Build.0 = Debug|x64
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Release|Win32.ActiveCfg = Release|Win32
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Release|Win32.Build.0 = Release|Win32
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Release|x64.ActiveCfg = Release|x64
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}.Release|x64.Build.0 = Release|x64
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Debug|Win32.ActiveCfg = Debug|Win32
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Debug|Win32.Build.0 = Debug|Win32
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Debug|x64.ActiveCfg = Debug|x64
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Debug|x64.Build.0 = Debug|x64
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Release|Win32.ActiveCfg = Release|Win32
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Release|Win32.Build.0 = Release|Win32
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Release|x64.ActiveCfg = Release|x64
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1}.Release|x64.Build.0 = Release|x64
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Debug|Win32.ActiveCfg = Debug|Win32
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Debug|Win32.Build.0 = Debug|Win32
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Debug|x64.ActiveCfg = Debug|x64
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Debug|x64.Build.0 = Debug|x64
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Release|Win32.ActiveCfg = Release|Win32
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Release|Win32.Build.0 = Release|Win32
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Release|x64.ActiveCfg = Release|x64
+		{65229ACC-5C9B-429C-B9DA-4710697637EB}.Release|x64.Build.0 = Release|x64
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Debug|Win32.ActiveCfg = Debug|Win32
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Debug|Win32.Build.0 = Debug|Win32
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Debug|x64.ActiveCfg = Debug|x64
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Debug|x64.Build.0 = Debug|x64
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Release|Win32.ActiveCfg = Release|Win32
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Release|Win32.Build.0 = Release|Win32
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Release|x64.ActiveCfg = Release|x64
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207}.Release|x64.Build.0 = Release|x64
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Debug|Win32.ActiveCfg = Debug|Win32
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Debug|Win32.Build.0 = Debug|Win32
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Debug|x64.ActiveCfg = Debug|x64
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Debug|x64.Build.0 = Debug|x64
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Release|Win32.ActiveCfg = Release|Win32
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Release|Win32.Build.0 = Release|Win32
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Release|x64.ActiveCfg = Release|x64
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4}.Release|x64.Build.0 = Release|x64
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Debug|Win32.ActiveCfg = Debug|Win32
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Debug|Win32.Build.0 = Debug|Win32
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Debug|x64.ActiveCfg = Debug|x64
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Debug|x64.Build.0 = Debug|x64
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Release|Win32.ActiveCfg = Release|Win32
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Release|Win32.Build.0 = Release|Win32
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Release|x64.ActiveCfg = Release|x64
+		{D8E2714A-11A7-478D-A966-EF6968FFB766}.Release|x64.Build.0 = Release|x64
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Debug|Win32.ActiveCfg = Debug|Win32
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Debug|Win32.Build.0 = Debug|Win32
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Debug|x64.ActiveCfg = Debug|x64
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Debug|x64.Build.0 = Debug|x64
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Release|Win32.ActiveCfg = Release|Win32
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Release|Win32.Build.0 = Release|Win32
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Release|x64.ActiveCfg = Release|x64
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17}.Release|x64.Build.0 = Release|x64
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Debug|Win32.ActiveCfg = Debug|Win32
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Debug|Win32.Build.0 = Debug|Win32
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Debug|x64.ActiveCfg = Debug|x64
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Debug|x64.Build.0 = Debug|x64
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Release|Win32.ActiveCfg = Release|Win32
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Release|Win32.Build.0 = Release|Win32
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Release|x64.ActiveCfg = Release|x64
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}.Release|x64.Build.0 = Release|x64
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Debug|Win32.ActiveCfg = Debug|Win32
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Debug|Win32.Build.0 = Debug|Win32
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Debug|x64.ActiveCfg = Debug|x64
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Debug|x64.Build.0 = Debug|x64
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Release|Win32.ActiveCfg = Release|Win32
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Release|Win32.Build.0 = Release|Win32
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Release|x64.ActiveCfg = Release|x64
+		{5303D6F1-D667-4E92-A501-8B396252156F}.Release|x64.Build.0 = Release|x64
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Debug|Win32.ActiveCfg = Debug|Win32
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Debug|Win32.Build.0 = Debug|Win32
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Debug|x64.ActiveCfg = Debug|x64
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Debug|x64.Build.0 = Debug|x64
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Release|Win32.ActiveCfg = Release|Win32
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Release|Win32.Build.0 = Release|Win32
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Release|x64.ActiveCfg = Release|x64
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}.Release|x64.Build.0 = Release|x64
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Debug|Win32.ActiveCfg = Debug|Win32
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Debug|Win32.Build.0 = Debug|Win32
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Debug|x64.ActiveCfg = Debug|x64
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Debug|x64.Build.0 = Debug|x64
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Release|Win32.ActiveCfg = Release|Win32
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Release|Win32.Build.0 = Release|Win32
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Release|x64.ActiveCfg = Release|x64
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}.Release|x64.Build.0 = Release|x64
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Debug|Win32.ActiveCfg = Debug|Win32
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Debug|Win32.Build.0 = Debug|Win32
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Debug|x64.ActiveCfg = Debug|x64
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Debug|x64.Build.0 = Debug|x64
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Release|Win32.ActiveCfg = Release|Win32
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Release|Win32.Build.0 = Release|Win32
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Release|x64.ActiveCfg = Release|x64
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155}.Release|x64.Build.0 = Release|x64
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Debug|Win32.ActiveCfg = Debug|Win32
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Debug|Win32.Build.0 = Debug|Win32
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Debug|x64.ActiveCfg = Debug|x64
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Debug|x64.Build.0 = Debug|x64
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Release|Win32.ActiveCfg = Release|Win32
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Release|Win32.Build.0 = Release|Win32
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Release|x64.ActiveCfg = Release|x64
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}.Release|x64.Build.0 = Release|x64
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Debug|Win32.ActiveCfg = Debug|Win32
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Debug|Win32.Build.0 = Debug|Win32
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Debug|x64.ActiveCfg = Debug|x64
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Debug|x64.Build.0 = Debug|x64
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Release|Win32.ActiveCfg = Release|Win32
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Release|Win32.Build.0 = Release|Win32
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Release|x64.ActiveCfg = Release|x64
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E}.Release|x64.Build.0 = Release|x64
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Debug|Win32.ActiveCfg = Debug|Win32
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Debug|Win32.Build.0 = Debug|Win32
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Debug|x64.ActiveCfg = Debug|x64
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Debug|x64.Build.0 = Debug|x64
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Release|Win32.ActiveCfg = Release|Win32
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Release|Win32.Build.0 = Release|Win32
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Release|x64.ActiveCfg = Release|x64
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}.Release|x64.Build.0 = Release|x64
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Debug|Win32.ActiveCfg = Debug|Win32
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Debug|Win32.Build.0 = Debug|Win32
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Debug|x64.ActiveCfg = Debug|x64
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Debug|x64.Build.0 = Debug|x64
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Release|Win32.ActiveCfg = Release|Win32
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Release|Win32.Build.0 = Release|Win32
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Release|x64.ActiveCfg = Release|x64
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}.Release|x64.Build.0 = Release|x64
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Debug|Win32.ActiveCfg = Debug|Win32
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Debug|Win32.Build.0 = Debug|Win32
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Debug|x64.ActiveCfg = Debug|x64
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Debug|x64.Build.0 = Debug|x64
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Release|Win32.ActiveCfg = Release|Win32
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Release|Win32.Build.0 = Release|Win32
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Release|x64.ActiveCfg = Release|x64
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310}.Release|x64.Build.0 = Release|x64
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Debug|Win32.ActiveCfg = Debug|Win32
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Debug|Win32.Build.0 = Debug|Win32
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Debug|x64.ActiveCfg = Debug|x64
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Debug|x64.Build.0 = Debug|x64
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Release|Win32.ActiveCfg = Release|Win32
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Release|Win32.Build.0 = Release|Win32
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Release|x64.ActiveCfg = Release|x64
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7}.Release|x64.Build.0 = Release|x64
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Debug|Win32.ActiveCfg = Debug|Win32
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Debug|Win32.Build.0 = Debug|Win32
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Debug|x64.ActiveCfg = Debug|x64
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Debug|x64.Build.0 = Debug|x64
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Release|Win32.ActiveCfg = Release|Win32
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Release|Win32.Build.0 = Release|Win32
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Release|x64.ActiveCfg = Release|x64
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}.Release|x64.Build.0 = Release|x64
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Debug|Win32.ActiveCfg = Debug|Win32
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Debug|Win32.Build.0 = Debug|Win32
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Debug|x64.ActiveCfg = Debug|x64
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Debug|x64.Build.0 = Debug|x64
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Release|Win32.ActiveCfg = Release|Win32
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Release|Win32.Build.0 = Release|Win32
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Release|x64.ActiveCfg = Release|x64
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1}.Release|x64.Build.0 = Release|x64
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Debug|Win32.ActiveCfg = Debug|Win32
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Debug|Win32.Build.0 = Debug|Win32
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Debug|x64.ActiveCfg = Debug|x64
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Debug|x64.Build.0 = Debug|x64
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Release|Win32.ActiveCfg = Release|Win32
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Release|Win32.Build.0 = Release|Win32
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Release|x64.ActiveCfg = Release|x64
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}.Release|x64.Build.0 = Release|x64
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Debug|Win32.ActiveCfg = Debug|Win32
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Debug|Win32.Build.0 = Debug|Win32
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Debug|x64.ActiveCfg = Debug|x64
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Debug|x64.Build.0 = Debug|x64
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Release|Win32.ActiveCfg = Release|Win32
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Release|Win32.Build.0 = Release|Win32
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Release|x64.ActiveCfg = Release|x64
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}.Release|x64.Build.0 = Release|x64
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Debug|Win32.Build.0 = Debug|Win32
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Debug|x64.ActiveCfg = Debug|x64
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Debug|x64.Build.0 = Debug|x64
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Release|Win32.ActiveCfg = Release|Win32
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Release|Win32.Build.0 = Release|Win32
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Release|x64.ActiveCfg = Release|x64
+		{781B56DF-15CE-4CBA-A008-0403029E558A}.Release|x64.Build.0 = Release|x64
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Debug|Win32.ActiveCfg = Debug|Win32
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Debug|Win32.Build.0 = Debug|Win32
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Debug|x64.ActiveCfg = Debug|x64
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Debug|x64.Build.0 = Debug|x64
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Release|Win32.ActiveCfg = Release|Win32
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Release|Win32.Build.0 = Release|Win32
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Release|x64.ActiveCfg = Release|x64
+		{BA36739B-F101-4C91-928D-678AB9521A22}.Release|x64.Build.0 = Release|x64
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Debug|Win32.ActiveCfg = Debug|Win32
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Debug|Win32.Build.0 = Debug|Win32
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Debug|x64.ActiveCfg = Debug|x64
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Debug|x64.Build.0 = Debug|x64
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Release|Win32.ActiveCfg = Release|Win32
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Release|Win32.Build.0 = Release|Win32
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Release|x64.ActiveCfg = Release|x64
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A}.Release|x64.Build.0 = Release|x64
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Debug|Win32.ActiveCfg = Debug|Win32
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Debug|Win32.Build.0 = Debug|Win32
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Debug|x64.ActiveCfg = Debug|x64
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Debug|x64.Build.0 = Debug|x64
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Release|Win32.ActiveCfg = Release|Win32
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Release|Win32.Build.0 = Release|Win32
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Release|x64.ActiveCfg = Release|x64
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}.Release|x64.Build.0 = Release|x64
+	EndGlobalSection
+	GlobalSection(SolutionProperties) = preSolution
+		HideSolutionNode = FALSE
+	EndGlobalSection
+	GlobalSection(NestedProjects) = preSolution
+		{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C} = {20B98358-3862-4D16-985F-ECE9DE5D9FEB}
+		{642392B3-C763-44C8-91F4-EA90C3651608} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{DE053D44-F9BD-4C1A-B44B-3157BE27AD02} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{7AF45D7B-8341-42CF-B382-B67E1399D8B1} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{65229ACC-5C9B-429C-B9DA-4710697637EB} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{218033A7-A6D0-45B4-88F6-F4FF5DD25207} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{111344DB-1F0B-460E-91DD-9DD36D2238A4} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{D8E2714A-11A7-478D-A966-EF6968FFB766} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{1F7B06CA-5529-4A3D-89CE-15161D4A01D9} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{0A06D231-FC40-4EC9-B0FC-F0D08270384E} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{3EDCB092-C785-41EB-8A83-C5B37A2FF310} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{33FF435B-A3CF-441E-964E-A7DA8735E7B1} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{BA36739B-F101-4C91-928D-678AB9521A22} = {25A7C026-702D-48A4-A1EC-81DE78F0664E}
+		{4459EB9F-0332-46C4-BF60-6CECA73C7D17} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{5303D6F1-D667-4E92-A501-8B396252156F} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{36EB9E03-E155-4487-AB1B-0B1B862B0155} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{0F52C42C-EEDA-4031-B0A0-F6CD53C81465} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{9E09B1EB-D3F3-4C38-B87F-AE642F509D04} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{9E7C038E-470E-4DF8-A887-3E1B8A02B78C} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{B0D287DB-451D-4005-9CE3-185D7602F0B7} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{781B56DF-15CE-4CBA-A008-0403029E558A} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{22788F46-AB6B-4278-B1C0-ED220AE85F4A} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6} = {0CF51D6D-1F80-4D2C-95BE-566641BD1F71}
+		{0CF51D6D-1F80-4D2C-95BE-566641BD1F71} = {9191A7C3-3B0A-45A5-99A2-72D1903AA7B7}
+		{25A7C026-702D-48A4-A1EC-81DE78F0664E} = {9191A7C3-3B0A-45A5-99A2-72D1903AA7B7}
+	EndGlobalSection
+EndGlobal
diff --git a/irdb-lib/pebliss/trunk/pe_lib/Makefile b/irdb-lib/pebliss/trunk/pe_lib/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..6105f28c22f8d2ff1ea5ad5dff479f0e207d907d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/Makefile
@@ -0,0 +1,24 @@
+OBJS = entropy.o file_version_info.o message_table.o pe_base.o pe_bound_import.o pe_checksum.o pe_debug.o pe_directory.o pe_dotnet.o pe_exception_directory.o pe_exports.o pe_imports.o pe_load_config.o pe_properties.o pe_properties_generic.o pe_relocations.o pe_factory.o pe_resources.o pe_resource_manager.o pe_resource_viewer.o pe_rich_data.o pe_section.o pe_tls.o utils.o version_info_editor.o version_info_viewer.o pe_exception.o resource_message_list_reader.o resource_string_table_reader.o resource_version_info_reader.o resource_version_info_writer.o resource_cursor_icon_reader.o resource_cursor_icon_writer.o resource_bitmap_writer.o resource_bitmap_reader.o resource_data_info.o pe_rebuilder.o
+LIBNAME = pebliss
+LIBPATH = ../lib
+CXXFLAGS = -O2 -Wall -fPIC -DPIC -I.
+
+ifdef PE_DEBUG
+CXXFLAGS  += -g -O0
+endif
+
+all: $(LIBPATH)/lib$(LIBNAME).a
+
+clean:
+	rm -f $(OBJS) lib$(LIBNAME).a
+	rm -rf ../lib
+
+lib$(LIBNAME).a: $(OBJS)
+	ar -cvr lib$(LIBNAME).a $(OBJS)
+	ranlib lib$(LIBNAME).a
+
+$(LIBPATH):
+	mkdir -p ../lib
+
+$(LIBPATH)/lib$(LIBNAME).a: lib$(LIBNAME).a $(LIBPATH)
+	cp -d lib$(LIBNAME).a ../lib
diff --git a/irdb-lib/pebliss/trunk/pe_lib/SConscript b/irdb-lib/pebliss/trunk/pe_lib/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..e5270eac2201cf4659e32e3f137e403b1187e567
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/SConscript
@@ -0,0 +1,59 @@
+import os
+
+Import('env')
+myenv=env
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+
+libname="pebliss"
+files=  '''
+	entropy.cpp
+	file_version_info.cpp
+	message_table.cpp
+	pe_base.cpp
+	pe_bound_import.cpp
+	pe_checksum.cpp
+	pe_debug.cpp
+	pe_directory.cpp
+	pe_dotnet.cpp
+	pe_exception.cpp
+	pe_exception_directory.cpp
+	pe_exports.cpp
+	pe_factory.cpp
+	pe_imports.cpp
+	pe_load_config.cpp
+	pe_properties.cpp
+	pe_properties_generic.cpp
+	pe_rebuilder.cpp
+	pe_relocations.cpp
+	pe_resource_manager.cpp
+	pe_resource_viewer.cpp
+	pe_resources.cpp
+	pe_rich_data.cpp
+	pe_section.cpp
+	pe_tls.cpp
+	resource_bitmap_reader.cpp
+	resource_bitmap_writer.cpp
+	resource_cursor_icon_reader.cpp
+	resource_cursor_icon_writer.cpp
+	resource_data_info.cpp
+	resource_message_list_reader.cpp
+	resource_string_table_reader.cpp
+	resource_version_info_reader.cpp
+	resource_version_info_writer.cpp
+	utils.cpp
+	version_info_editor.cpp
+	version_info_viewer.cpp
+	'''
+
+cpppath=''' 
+	$SECURITY_TRANSFORMS_HOME/pebliss/trunk/pe_lib
+	'''
+
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+myenv.Append(CCFLAGS=" -w ")
+lib=myenv.SharedLibrary(libname, Split(files))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+Default(install)
+
diff --git a/irdb-lib/pebliss/trunk/pe_lib/SConstruct b/irdb-lib/pebliss/trunk/pe_lib/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..c0dd68a00d406b0148a93709cf916ad6d05f282c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/SConstruct
@@ -0,0 +1,6 @@
+
+
+
+env=Environment()
+Export('env')
+SConscript("SConscript")
diff --git a/irdb-lib/pebliss/trunk/pe_lib/entropy.cpp b/irdb-lib/pebliss/trunk/pe_lib/entropy.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..cdd8efb8a95a94ab734402b5725e4415148f4310
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/entropy.cpp
@@ -0,0 +1,90 @@
+#include <cmath>
+#include "entropy.h"
+#include "utils.h"
+
+namespace pe_bliss
+{
+//Calculates entropy for PE image section
+double entropy_calculator::calculate_entropy(const section& s)
+{
+	if(s.get_raw_data().empty()) //Don't count entropy for empty sections
+		throw pe_exception("Section is empty", pe_exception::section_is_empty);
+
+	return calculate_entropy(s.get_raw_data().data(), s.get_raw_data().length());
+}
+
+//Calculates entropy for istream (from current position of stream)
+double entropy_calculator::calculate_entropy(std::istream& file)
+{
+	uint32_t byte_count[256] = {0}; //Byte count for each of 255 bytes
+
+	if(file.bad())
+		throw pe_exception("Stream is bad", pe_exception::stream_is_bad);
+
+	std::streamoff pos = file.tellg();
+
+	std::streamoff length = pe_utils::get_file_size(file);
+	length -= file.tellg();
+
+	if(!length) //Don't calculate entropy for empty buffers
+		throw pe_exception("Data length is zero", pe_exception::data_is_empty);
+
+	//Count bytes
+	for(std::streamoff i = 0; i != length; ++i)
+		++byte_count[static_cast<unsigned char>(file.get())];
+
+	file.seekg(pos);
+
+	return calculate_entropy(byte_count, length);
+}
+
+//Calculates entropy for data block
+double entropy_calculator::calculate_entropy(const char* data, size_t length)
+{
+	uint32_t byte_count[256] = {0}; //Byte count for each of 255 bytes
+
+	if(!length) //Don't calculate entropy for empty buffers
+		throw pe_exception("Data length is zero", pe_exception::data_is_empty);
+
+	//Count bytes
+	for(size_t i = 0; i != length; ++i)
+		++byte_count[static_cast<unsigned char>(data[i])];
+
+	return calculate_entropy(byte_count, length);
+}
+
+//Calculates entropy for this PE file (only section data)
+double entropy_calculator::calculate_entropy(const pe_base& pe)
+{
+	uint32_t byte_count[256] = {0}; //Byte count for each of 255 bytes
+
+	size_t total_data_length = 0;
+
+	//Count bytes for each section
+	for(section_list::const_iterator it = pe.get_image_sections().begin(); it != pe.get_image_sections().end(); ++it)
+	{
+		const std::string& data = (*it).get_raw_data();
+		size_t length = data.length();
+		total_data_length += length;
+		for(size_t i = 0; i != length; ++i)
+			++byte_count[static_cast<unsigned char>(data[i])];
+	}
+
+	return calculate_entropy(byte_count, total_data_length);
+}
+
+//Calculates entropy from bytes count
+double entropy_calculator::calculate_entropy(const uint32_t byte_count[256], std::streamoff total_length)
+{
+	double entropy = 0.; //Entropy result value
+	//Calculate entropy
+	for(uint32_t i = 0; i < 256; ++i)
+	{
+		double temp = static_cast<double>(byte_count[i]) / total_length;
+		if(temp > 0.)
+			entropy += std::abs(temp * (std::log(temp) * pe_utils::log_2));
+	}
+
+	return entropy;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/entropy.h b/irdb-lib/pebliss/trunk/pe_lib/entropy.h
new file mode 100644
index 0000000000000000000000000000000000000000..749ad4c588f23e1a869dca74af71eff6bd805f20
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/entropy.h
@@ -0,0 +1,34 @@
+#ifndef pebliss_entropy_h
+#define pebliss_entropy_h
+#pragma once
+
+#include <istream>
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+class entropy_calculator
+{
+public:
+	//Calculates entropy for PE image section
+	static double calculate_entropy(const section& s);
+
+	//Calculates entropy for istream (from current position of stream)
+	static double calculate_entropy(std::istream& file);
+
+	//Calculates entropy for data block
+	static double calculate_entropy(const char* data, size_t length);
+
+	//Calculates entropy for this PE file (only section data)
+	static double calculate_entropy(const pe_base& pe);
+
+private:
+	entropy_calculator();
+	entropy_calculator(const entropy_calculator&);
+	entropy_calculator& operator=(const entropy_calculator&);
+
+	//Calculates entropy from bytes count
+	static double calculate_entropy(const uint32_t byte_count[256], std::streamoff total_length);
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/file_version_info.cpp b/irdb-lib/pebliss/trunk/pe_lib/file_version_info.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..50a02f89087e84b00dd8fbeb52ea7a3a85fd679c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/file_version_info.cpp
@@ -0,0 +1,419 @@
+#include "file_version_info.h"
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Default constructor
+file_version_info::file_version_info()
+	:file_version_ms_(0), file_version_ls_(0),
+	product_version_ms_(0), product_version_ls_(0),
+	file_flags_(0),
+	file_os_(0),
+	file_type_(0), file_subtype_(0),
+	file_date_ms_(0), file_date_ls_(0)
+{}
+
+//Constructor from Windows fixed version info structure
+file_version_info::file_version_info(const vs_fixedfileinfo& info)
+	:file_version_ms_(info.dwFileVersionMS), file_version_ls_(info.dwFileVersionLS),
+	product_version_ms_(info.dwProductVersionMS), product_version_ls_(info.dwProductVersionLS),
+	file_flags_(info.dwFileFlags),
+	file_os_(info.dwFileOS),
+	file_type_(info.dwFileType), file_subtype_(info.dwFileSubtype),
+	file_date_ms_(info.dwFileDateMS), file_date_ls_(info.dwFileDateLS)
+{}
+
+//Returns true if file is debug-built
+bool file_version_info::is_debug() const
+{
+	return file_flags_ & vs_ff_debug ? true : false;
+}
+
+//Returns true if file is release-built
+bool file_version_info::is_prerelease() const
+{
+	return file_flags_ & vs_ff_prerelease ? true : false;
+}
+
+//Returns true if file is patched
+bool file_version_info::is_patched() const
+{
+	return file_flags_ & vs_ff_patched ? true : false;
+}
+
+//Returns true if private build
+bool file_version_info::is_private_build() const
+{
+	return file_flags_ & vs_ff_privatebuild ? true : false;
+}
+
+//Returns true if special build
+bool file_version_info::is_special_build() const
+{
+	return file_flags_ & vs_ff_specialbuild ? true : false;
+}
+
+//Returns true if info inferred
+bool file_version_info::is_info_inferred() const
+{
+	return file_flags_ & vs_ff_infoinferred ? true : false;
+}
+
+//Retuens file flags (raw DWORD)
+uint32_t file_version_info::get_file_flags() const
+{
+	return file_flags_;
+}
+
+//Returns file version most significant DWORD
+uint32_t file_version_info::get_file_version_ms() const
+{
+	return file_version_ms_;
+}
+
+//Returns file version least significant DWORD
+uint32_t file_version_info::get_file_version_ls() const
+{
+	return file_version_ls_;
+}
+
+//Returns product version most significant DWORD
+uint32_t file_version_info::get_product_version_ms() const
+{
+	return product_version_ms_;
+}
+
+//Returns product version least significant DWORD
+uint32_t file_version_info::get_product_version_ls() const
+{
+	return product_version_ls_;
+}
+
+//Returns file OS type (raw DWORD)
+uint32_t file_version_info::get_file_os_raw() const
+{
+	return file_os_;
+}
+
+//Returns file OS type
+file_version_info::file_os_type file_version_info::get_file_os() const
+{
+	//Determine file operation system type
+	switch(file_os_)
+	{
+	case vos_dos:
+		return file_os_dos;
+
+	case vos_os216:
+		return file_os_os216;
+
+	case vos_os232:
+		return file_os_os232;
+
+	case vos_nt:
+		return file_os_nt;
+
+	case vos_wince:
+		return file_os_wince;
+
+	case vos__windows16:
+		return file_os_win16;
+
+	case vos__pm16:
+		return file_os_pm16;
+
+	case vos__pm32:
+		return file_os_pm32;
+
+	case vos__windows32:
+		return file_os_win32;
+
+	case vos_dos_windows16:
+		return file_os_dos_win16;
+
+	case vos_dos_windows32:
+		return file_os_dos_win32;
+
+	case vos_os216_pm16:
+		return file_os_os216_pm16;
+
+	case vos_os232_pm32:
+		return file_os_os232_pm32;
+
+	case vos_nt_windows32:
+		return file_os_nt_win32;
+	}
+
+	return file_os_unknown;
+}
+
+//Returns file type (raw DWORD)
+uint32_t file_version_info::get_file_type_raw() const
+{
+	return file_type_;
+}
+
+//Returns file type
+file_version_info::file_type file_version_info::get_file_type() const
+{
+	//Determine file type
+	switch(file_type_)
+	{
+	case vft_app:
+		return file_type_application;
+
+	case vft_dll:
+		return file_type_dll;
+
+	case vft_drv:
+		return file_type_driver;
+
+	case vft_font:
+		return file_type_font;
+
+	case vft_vxd:
+		return file_type_vxd;
+
+	case vft_static_lib:
+		return file_type_static_lib;
+	}
+
+	return file_type_unknown;
+}
+
+//Returns file subtype (usually non-zero for drivers and fonts)
+uint32_t file_version_info::get_file_subtype() const
+{
+	return file_subtype_;
+}
+
+//Returns file date most significant DWORD
+uint32_t file_version_info::get_file_date_ms() const
+{
+	return file_date_ms_;
+}
+
+//Returns file date least significant DWORD
+uint32_t file_version_info::get_file_date_ls() const
+{
+	return file_date_ls_;
+}
+
+//Helper to set file flag
+void file_version_info::set_file_flag(uint32_t flag)
+{
+	file_flags_ |= flag;
+}
+
+//Helper to clear file flag
+void file_version_info::clear_file_flag(uint32_t flag)
+{
+	file_flags_ &= ~flag;
+}
+
+//Helper to set or clear file flag
+void file_version_info::set_file_flag(uint32_t flag, bool set_flag)
+{
+	set_flag ? set_file_flag(flag) : clear_file_flag(flag);
+}
+
+//Sets if file is debug-built
+void file_version_info::set_debug(bool debug)
+{
+	set_file_flag(vs_ff_debug, debug);
+}
+
+//Sets if file is prerelease
+void file_version_info::set_prerelease(bool prerelease)
+{
+	set_file_flag(vs_ff_prerelease, prerelease);
+}
+
+//Sets if file is patched
+void file_version_info::set_patched(bool patched)
+{
+	set_file_flag(vs_ff_patched, patched);
+}
+
+//Sets if private build
+void file_version_info::set_private_build(bool private_build)
+{
+	set_file_flag(vs_ff_privatebuild, private_build);
+}
+
+//Sets if special build
+void file_version_info::set_special_build(bool special_build)
+{
+	set_file_flag(vs_ff_specialbuild, special_build);
+}
+
+//Sets if info inferred
+void file_version_info::set_info_inferred(bool info_inferred)
+{
+	set_file_flag(vs_ff_infoinferred, info_inferred);
+}
+
+//Sets flags (raw DWORD)
+void file_version_info::set_file_flags(uint32_t file_flags)
+{
+	file_flags_ = file_flags;
+}
+
+//Sets file version most significant DWORD
+void file_version_info::set_file_version_ms(uint32_t file_version_ms)
+{
+	file_version_ms_ = file_version_ms;
+}
+
+//Sets file version least significant DWORD
+void file_version_info::set_file_version_ls(uint32_t file_version_ls)
+{
+	file_version_ls_ = file_version_ls;
+}
+
+//Sets product version most significant DWORD
+void file_version_info::set_product_version_ms(uint32_t product_version_ms)
+{
+	product_version_ms_ = product_version_ms;
+}
+
+//Sets product version least significant DWORD
+void file_version_info::set_product_version_ls(uint32_t product_version_ls)
+{
+	product_version_ls_ = product_version_ls;
+}
+
+//Sets file OS type (raw DWORD)
+void file_version_info::set_file_os_raw(uint32_t file_os)
+{
+	file_os_ = file_os;
+}
+
+//Sets file OS type
+void file_version_info::set_file_os(file_os_type file_os)
+{
+	//Determine file operation system type
+	switch(file_os)
+	{
+	case file_os_dos:
+		file_os_ = vos_dos;
+		return;
+
+	case file_os_os216:
+		file_os_ = vos_os216;
+		return;
+
+	case file_os_os232:
+		file_os_ = vos_os232;
+		return;
+
+	case file_os_nt:
+		file_os_ = vos_nt;
+		return;
+
+	case file_os_wince:
+		file_os_ = vos_wince;
+		return;
+
+	case file_os_win16:
+		file_os_ = vos__windows16;
+		return;
+		
+	case file_os_pm16:
+		file_os_ = vos__pm16;
+		return;
+
+	case file_os_pm32:
+		file_os_ = vos__pm32;
+		return;
+
+	case file_os_win32:
+		file_os_ = vos__windows32;
+		return;
+
+	case file_os_dos_win16:
+		file_os_ = vos_dos_windows16;
+		return;
+
+	case file_os_dos_win32:
+		file_os_ = vos_dos_windows32;
+		return;
+
+	case file_os_os216_pm16:
+		file_os_ = vos_os216_pm16;
+		return;
+
+	case file_os_os232_pm32:
+		file_os_ = vos_os232_pm32;
+		return;
+
+	case file_os_nt_win32:
+		file_os_ = vos_nt_windows32;
+		return;
+
+	default:
+		return;
+	}
+}
+
+//Sets file type (raw DWORD)
+void file_version_info::set_file_type_raw(uint32_t file_type)
+{
+	file_type_ = file_type;
+}
+
+//Sets file type
+void file_version_info::set_file_type(file_type file_type)
+{
+	//Determine file type
+	switch(file_type)
+	{
+	case file_type_application:
+		file_type_ = vft_app;
+		return;
+		
+	case file_type_dll:
+		file_type_ = vft_dll;
+		return;
+
+	case file_type_driver:
+		file_type_ = vft_drv;
+		return;
+
+	case file_type_font:
+		file_type_ = vft_font;
+		return;
+
+	case file_type_vxd:
+		file_type_ = vft_vxd;
+		return;
+
+	case file_type_static_lib:
+		file_type_ = vft_static_lib;
+		return;
+
+	default:
+		return;
+	}
+}
+
+//Sets file subtype (usually non-zero for drivers and fonts)
+void file_version_info::set_file_subtype(uint32_t file_subtype)
+{
+	file_subtype_ = file_subtype;
+}
+
+//Sets file date most significant DWORD
+void file_version_info::set_file_date_ms(uint32_t file_date_ms)
+{
+	file_date_ms_ = file_date_ms;
+}
+
+//Sets file date least significant DWORD
+void file_version_info::set_file_date_ls(uint32_t file_date_ls)
+{
+	file_date_ls_ = file_date_ls;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/file_version_info.h b/irdb-lib/pebliss/trunk/pe_lib/file_version_info.h
new file mode 100644
index 0000000000000000000000000000000000000000..34fc2de03f7afdbf7c3fe045d7f159203ba05aea
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/file_version_info.h
@@ -0,0 +1,181 @@
+#ifndef pebliss_file_version_info_h
+#define pebliss_file_version_info_h
+#pragma once
+#include <string>
+#include <map>
+#include "stdint_defs.h"
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+//Structure representing fixed file version info
+class file_version_info
+{
+public:
+	//Enumeration of file operating system types
+	enum file_os_type
+	{
+		file_os_unknown,
+		file_os_dos,
+		file_os_os216,
+		file_os_os232,
+		file_os_nt,
+		file_os_wince,
+		file_os_win16,
+		file_os_pm16,
+		file_os_pm32,
+		file_os_win32,
+		file_os_dos_win16,
+		file_os_dos_win32,
+		file_os_os216_pm16,
+		file_os_os232_pm32,
+		file_os_nt_win32
+	};
+
+	//Enumeration of file types
+	enum file_type
+	{
+		file_type_unknown,
+		file_type_application,
+		file_type_dll,
+		file_type_driver,
+		file_type_font,
+		file_type_vxd,
+		file_type_static_lib
+	};
+
+public:
+	//Default constructor
+	file_version_info();
+	//Constructor from Windows fixed version info structure
+	explicit file_version_info(const pe_win::vs_fixedfileinfo& info);
+
+public: //Getters
+	//Returns true if file is debug-built
+	bool is_debug() const;
+	//Returns true if file is prerelease
+	bool is_prerelease() const;
+	//Returns true if file is patched
+	bool is_patched() const;
+	//Returns true if private build
+	bool is_private_build() const;
+	//Returns true if special build
+	bool is_special_build() const;
+	//Returns true if info inferred
+	bool is_info_inferred() const;
+	//Retuens file flags (raw DWORD)
+	uint32_t get_file_flags() const;
+
+	//Returns file version most significant DWORD
+	uint32_t get_file_version_ms() const;
+	//Returns file version least significant DWORD
+	uint32_t get_file_version_ls() const;
+	//Returns product version most significant DWORD
+	uint32_t get_product_version_ms() const;
+	//Returns product version least significant DWORD
+	uint32_t get_product_version_ls() const;
+
+	//Returns file OS type (raw DWORD)
+	uint32_t get_file_os_raw() const;
+	//Returns file OS type
+	file_os_type get_file_os() const;
+
+	//Returns file type (raw DWORD)
+	uint32_t get_file_type_raw() const;
+	//Returns file type
+	file_type get_file_type() const;
+
+	//Returns file subtype (usually non-zero for drivers and fonts)
+	uint32_t get_file_subtype() const;
+
+	//Returns file date most significant DWORD
+	uint32_t get_file_date_ms() const;
+	//Returns file date least significant DWORD
+	uint32_t get_file_date_ls() const;
+
+	//Returns file version string
+	template<typename T>
+	const std::basic_string<T> get_file_version_string() const
+	{
+		return get_version_string<T>(file_version_ms_, file_version_ls_);
+	}
+
+	//Returns product version string
+	template<typename T>
+	const std::basic_string<T> get_product_version_string() const
+	{
+		return get_version_string<T>(product_version_ms_, product_version_ls_);
+	}
+		
+public: //Setters
+	//Sets if file is debug-built
+	void set_debug(bool debug);
+	//Sets if file is prerelease
+	void set_prerelease(bool prerelease);
+	//Sets if file is patched
+	void set_patched(bool patched);
+	//Sets if private build
+	void set_private_build(bool private_build);
+	//Sets if special build
+	void set_special_build(bool special_build);
+	//Sets if info inferred
+	void set_info_inferred(bool info_inferred);
+	//Sets flags (raw DWORD)
+	void set_file_flags(uint32_t file_flags);
+
+	//Sets file version most significant DWORD
+	void set_file_version_ms(uint32_t file_version_ms);
+	//Sets file version least significant DWORD
+	void set_file_version_ls(uint32_t file_version_ls);
+	//Sets product version most significant DWORD
+	void set_product_version_ms(uint32_t product_version_ms);
+	//Sets product version least significant DWORD
+	void set_product_version_ls(uint32_t product_version_ls);
+
+	//Sets file OS type (raw DWORD)
+	void set_file_os_raw(uint32_t file_os);
+	//Sets file OS type
+	void set_file_os(file_os_type file_os);
+
+	//Sets file type (raw DWORD)
+	void set_file_type_raw(uint32_t file_type);
+	//Sets file type
+	void set_file_type(file_type file_type);
+
+	//Sets file subtype (usually non-zero for drivers and fonts)
+	void set_file_subtype(uint32_t file_subtype);
+
+	//Sets file date most significant DWORD
+	void set_file_date_ms(uint32_t file_date_ms);
+	//Sets file date least significant DWORD
+	void set_file_date_ls(uint32_t file_date_ls);
+
+private:
+	//Helper to convert version DWORDs to string
+	template<typename T>
+	static const std::basic_string<T> get_version_string(uint32_t ms, uint32_t ls)
+	{
+		std::basic_stringstream<T> ss;
+		ss << (ms >> 16) << static_cast<T>(L'.')
+			<< (ms & 0xFFFF) << static_cast<T>(L'.')
+			<< (ls >> 16) << static_cast<T>(L'.')
+			<< (ls & 0xFFFF);
+		return ss.str();
+	}
+
+	//Helper to set file flag
+	void set_file_flag(uint32_t flag);
+	//Helper to clear file flag
+	void clear_file_flag(uint32_t flag);
+	//Helper to set or clear file flag
+	void set_file_flag(uint32_t flag, bool set_flag);
+
+	uint32_t file_version_ms_, file_version_ls_,
+		product_version_ms_, product_version_ls_;
+	uint32_t file_flags_;
+	uint32_t file_os_;
+	uint32_t file_type_, file_subtype_;
+	uint32_t file_date_ms_, file_date_ls_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/message_table.cpp b/irdb-lib/pebliss/trunk/pe_lib/message_table.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..940387dd281c1aa146fe52bdc0e74704972e81d5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/message_table.cpp
@@ -0,0 +1,60 @@
+#include "message_table.h"
+#include "utils.h"
+
+namespace pe_bliss
+{
+//Default constructor
+message_table_item::message_table_item()
+	:unicode_(false)
+{}
+
+//Constructor from ANSI string
+message_table_item::message_table_item(const std::string& str)
+	:unicode_(false), ansi_str_(str)
+{
+	pe_utils::strip_nullbytes(ansi_str_);
+}
+
+//Constructor from UNICODE string
+message_table_item::message_table_item(const std::wstring& str)
+	:unicode_(true), unicode_str_(str)
+{
+	pe_utils::strip_nullbytes(unicode_str_);
+}
+
+//Returns true if contained string is unicode
+bool message_table_item::is_unicode() const
+{
+	return unicode_;
+}
+
+//Returns ANSI string
+const std::string& message_table_item::get_ansi_string() const
+{
+	return ansi_str_;
+}
+
+//Returns UNICODE string
+const std::wstring& message_table_item::get_unicode_string() const
+{
+	return unicode_str_;
+}
+
+//Sets ANSI string (clears UNICODE one)
+void message_table_item::set_string(const std::string& str)
+{
+	ansi_str_ = str;
+	pe_utils::strip_nullbytes(ansi_str_);
+	unicode_str_.clear();
+	unicode_ = false;
+}
+
+//Sets UNICODE string (clears ANSI one)
+void message_table_item::set_string(const std::wstring& str)
+{
+	unicode_str_ = str;
+	pe_utils::strip_nullbytes(unicode_str_);
+	ansi_str_.clear();
+	unicode_ = true;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/message_table.h b/irdb-lib/pebliss/trunk/pe_lib/message_table.h
new file mode 100644
index 0000000000000000000000000000000000000000..91f7d11daf2a0cae770b01cb191ebf1077de093d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/message_table.h
@@ -0,0 +1,42 @@
+#ifndef pebliss_message_table_h
+#define pebliss_message_table_h
+#pragma once
+#ifndef pe_bliss_message_table_h
+#define pe_bliss_message_table_h
+
+#include <string>
+#include <map>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+//Structure representing message table string
+class message_table_item
+{
+public:
+	//Default constructor
+	message_table_item();
+	//Constructors from ANSI and UNICODE strings
+	explicit message_table_item(const std::string& str);
+	explicit message_table_item(const std::wstring& str);
+
+	//Returns true if string is UNICODE
+	bool is_unicode() const;
+	//Returns ANSI string
+	const std::string& get_ansi_string() const;
+	//Returns UNICODE string
+	const std::wstring& get_unicode_string() const;
+
+public:
+	//Sets ANSI or UNICODE string
+	void set_string(const std::string& str);
+	void set_string(const std::wstring& str);
+
+private:
+	bool unicode_;
+	std::string ansi_str_;
+	std::wstring unicode_str_;
+};
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_base.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_base.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e3ba9aaf34f874cb5c3a0d802385d2dc041dcc2a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_base.cpp
@@ -0,0 +1,1659 @@
+#include <string>
+#include <vector>
+#include <istream>
+#include <ostream>
+#include <algorithm>
+#include <cmath>
+#include <set>
+#include <string.h>
+#include "pe_exception.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Constructor
+pe_base::pe_base(std::istream& file, const pe_properties& props, bool read_debug_raw_data)
+{
+	props_ = props.duplicate().release();
+
+	//Save istream state
+	std::ios_base::iostate state = file.exceptions();
+	std::streamoff old_offset = file.tellg();
+
+	try
+	{
+		file.exceptions(std::ios::goodbit);
+		//Read DOS header, PE headers and section data
+		read_dos_header(file);
+		read_pe(file, read_debug_raw_data);
+	}
+	catch(const std::exception&)
+	{
+		//If something went wrong, restore istream state
+		file.seekg(old_offset);
+		file.exceptions(state);
+		file.clear();
+		//Rethrow
+		throw;
+	}
+
+	//Restore istream state
+	file.seekg(old_offset);
+	file.exceptions(state);
+	file.clear();
+}
+
+pe_base::pe_base(const pe_properties& props, uint32_t section_alignment, bool dll, uint16_t subsystem)
+{
+	props_ = props.duplicate().release();
+	props_->create_pe(section_alignment, subsystem);
+
+	has_overlay_ = false;
+	memset(&dos_header_, 0, sizeof(dos_header_));
+
+	dos_header_.e_magic = 0x5A4D; //"MZ"
+	//Magic numbers from MSVC++ build
+	dos_header_.e_maxalloc = 0xFFFF;
+	dos_header_.e_cblp = 0x90;
+	dos_header_.e_cp = 3;
+	dos_header_.e_cparhdr = 4;
+	dos_header_.e_sp = 0xB8;
+	dos_header_.e_lfarlc = 64;
+
+	set_characteristics(image_file_executable_image | image_file_relocs_stripped);
+
+	if(get_pe_type() == pe_type_32)
+		set_characteristics_flags(image_file_32bit_machine);
+
+	if(dll)
+		set_characteristics_flags(image_file_dll);
+
+	set_subsystem_version(5, 1); //WinXP
+	set_os_version(5, 1); //WinXP
+}
+
+pe_base::pe_base(const pe_base& pe)
+	:dos_header_(pe.dos_header_),
+	rich_overlay_(pe.rich_overlay_),
+	sections_(pe.sections_),
+	has_overlay_(pe.has_overlay_),
+	full_headers_data_(pe.full_headers_data_),
+	debug_data_(pe.debug_data_),
+	props_(0)
+{
+	props_ = pe.props_->duplicate().release();
+}
+
+pe_base& pe_base::operator=(const pe_base& pe)
+{
+	dos_header_ = pe.dos_header_;
+	rich_overlay_ = pe.rich_overlay_;
+	sections_ = pe.sections_;
+	has_overlay_ = pe.has_overlay_;
+	full_headers_data_ = pe.full_headers_data_;
+	debug_data_ = pe.debug_data_;
+	delete props_;
+	props_ = 0;
+	props_ = pe.props_->duplicate().release();
+
+	return *this;
+}
+
+pe_base::~pe_base()
+{
+	delete props_;
+}
+
+//Returns dos header
+const image_dos_header& pe_base::get_dos_header() const
+{
+	return dos_header_;
+}
+
+//Returns dos header
+image_dos_header& pe_base::get_dos_header()
+{
+	return dos_header_;
+}
+
+//Returns PE headers start position (e_lfanew)
+int32_t pe_base::get_pe_header_start() const
+{
+	return dos_header_.e_lfanew;
+}
+
+//Strips MSVC stub overlay
+void pe_base::strip_stub_overlay()
+{
+	rich_overlay_.clear();
+}
+
+//Fills MSVC stub overlay with character c
+void pe_base::fill_stub_overlay(char c)
+{
+	if(rich_overlay_.length())
+		rich_overlay_.assign(rich_overlay_.length(), c);
+}
+
+//Sets stub MSVS overlay
+void pe_base::set_stub_overlay(const std::string& data)
+{
+	rich_overlay_ = data;
+}
+
+//Returns stub overlay
+const std::string& pe_base::get_stub_overlay() const
+{
+	return rich_overlay_;
+}
+
+//Realigns all sections
+void pe_base::realign_all_sections()
+{
+	for(unsigned int i = 0; i < sections_.size(); i++)
+		realign_section(i);
+}
+
+//Returns number of sections from PE header
+uint16_t pe_base::get_number_of_sections() const
+{
+	return props_->get_number_of_sections();
+}
+
+//Updates number of sections in PE header
+uint16_t pe_base::update_number_of_sections()
+{
+	uint16_t new_number = static_cast<uint16_t>(sections_.size());
+	props_->set_number_of_sections(new_number);
+	return new_number;
+}
+
+//Returns section alignment
+uint32_t pe_base::get_section_alignment() const
+{
+	return props_->get_section_alignment();
+}
+
+//Returns image sections list
+section_list& pe_base::get_image_sections()
+{
+	return sections_;
+}
+
+//Returns image sections list
+const section_list& pe_base::get_image_sections() const
+{
+	return sections_;
+}
+
+//Realigns section by index
+void pe_base::realign_section(uint32_t index)
+{
+	//Check index
+	if(sections_.size() <= index)
+		throw pe_exception("Section not found", pe_exception::section_not_found);
+
+	//Get section iterator
+	section_list::iterator it = sections_.begin() + index;
+	section& s = *it;
+
+	//Calculate, how many null bytes we have in the end of raw section data
+	std::size_t strip = 0;
+	for(std::size_t i = (*it).get_raw_data().length(); i >= 1; --i)
+	{
+		if(s.get_raw_data()[i - 1] == 0)
+			strip++;
+		else
+			break;
+	}
+
+	if(it == sections_.end() - 1) //If we're realigning the last section
+	{
+		//We can strip ending null bytes
+		s.set_size_of_raw_data(static_cast<uint32_t>(s.get_raw_data().length() - strip));
+		s.get_raw_data().resize(s.get_raw_data().length() - strip, 0);
+	}
+	else
+	{
+		//Else just set size of raw data
+		uint32_t raw_size_aligned = s.get_aligned_raw_size(get_file_alignment());
+		s.set_size_of_raw_data(raw_size_aligned);
+		s.get_raw_data().resize(raw_size_aligned, 0);
+	}
+}
+
+//Returns file alignment
+uint32_t pe_base::get_file_alignment() const
+{
+	return props_->get_file_alignment();
+}
+
+//Sets file alignment
+void pe_base::set_file_alignment(uint32_t alignment)
+{
+	//Check alignment
+	if(alignment < minimum_file_alignment)
+		throw pe_exception("File alignment can't be less than 512", pe_exception::incorrect_file_alignment);
+
+	if(!pe_utils::is_power_of_2(alignment))
+		throw pe_exception("File alignment must be a power of 2", pe_exception::incorrect_file_alignment);
+
+	if(alignment > get_section_alignment())
+		throw pe_exception("File alignment must be <= section alignment", pe_exception::incorrect_file_alignment);
+
+	//Set file alignment without any additional checks
+	set_file_alignment_unchecked(alignment);
+}
+
+//Returns size of image
+uint32_t pe_base::get_size_of_image() const
+{
+	return props_->get_size_of_image();
+}
+
+//Returns image entry point
+uint32_t pe_base::get_ep() const
+{
+	return props_->get_ep();
+}
+
+//Sets image entry point (just a value of PE header)
+void pe_base::set_ep(uint32_t new_ep)
+{
+	props_->set_ep(new_ep);
+}
+
+//Returns number of RVA and sizes (number of DATA_DIRECTORY entries)
+uint32_t pe_base::get_number_of_rvas_and_sizes() const
+{
+	return props_->get_number_of_rvas_and_sizes();
+}
+
+//Sets number of RVA and sizes (number of DATA_DIRECTORY entries)
+void pe_base::set_number_of_rvas_and_sizes(uint32_t number)
+{
+	props_->set_number_of_rvas_and_sizes(number);
+}
+
+//Returns PE characteristics
+uint16_t pe_base::get_characteristics() const
+{
+	return props_->get_characteristics();
+}
+
+//Sets PE characteristics (a value inside header)
+void pe_base::set_characteristics(uint16_t ch)
+{
+	props_->set_characteristics(ch);
+}
+
+//Returns section from RVA
+section& pe_base::section_from_rva(uint32_t rva)
+{
+	//Search for section
+	for(section_list::iterator i = sections_.begin(); i != sections_.end(); ++i)
+	{
+		section& s = *i;
+		//Return section if found
+		if(rva >= s.get_virtual_address() && rva < s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()))
+			return s;
+	}
+
+	throw pe_exception("No section found by presented address", pe_exception::no_section_found);
+}
+
+//Returns section from RVA
+const section& pe_base::section_from_rva(uint32_t rva) const
+{
+	//Search for section
+	for(section_list::const_iterator i = sections_.begin(); i != sections_.end(); ++i)
+	{
+		const section& s = *i;
+		//Return section if found
+		if(rva >= s.get_virtual_address() && rva < s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()))
+			return s;
+	}
+
+	throw pe_exception("No section found by presented address", pe_exception::no_section_found);
+}
+
+//Returns section from directory ID
+section& pe_base::section_from_directory(uint32_t directory_id)
+{
+	return section_from_rva(get_directory_rva(directory_id));		
+}
+
+//Returns section from directory ID
+const section& pe_base::section_from_directory(uint32_t directory_id) const
+{
+	return section_from_rva(get_directory_rva(directory_id));	
+}
+
+//Sets section virtual size (actual for the last one of this PE or for unbound section)
+void pe_base::set_section_virtual_size(section& s, uint32_t vsize)
+{
+	//Check if we're changing virtual size of the last section
+	//Of course, we can change virtual size of section that's not bound to this PE file
+	if(sections_.empty() || std::find_if(sections_.begin(), sections_.end() - 1, section_ptr_finder(s)) != sections_.end() - 1)
+		throw pe_exception("Can't change virtual size of any section, except last one", pe_exception::error_changing_section_virtual_size);
+
+	//If we're setting virtual size to zero
+	if(vsize == 0)
+	{
+		//Check if section is empty
+		if(s.empty())
+			throw pe_exception("Cannot set virtual size of empty section to zero", pe_exception::error_changing_section_virtual_size);
+
+		//Set virtual size equal to aligned size of raw data
+		s.set_virtual_size(s.get_size_of_raw_data());
+	}
+	else
+	{
+		s.set_virtual_size(vsize);
+	}
+
+	//Update image size if we're changing virtual size for the last section of this PE
+	if(!sections_.empty() || &s == &(*(sections_.end() - 1)))
+		update_image_size();
+}
+
+//Expands section raw or virtual size to hold data from specified RVA with specified size
+//Section must be free (not bound to any image)
+//or the last section of this image
+bool pe_base::expand_section(section& s, uint32_t needed_rva, uint32_t needed_size, section_expand_type expand)
+{
+	//Check if we're changing the last section
+	//Of course, we can change the section that's not bound to this PE file
+	if(sections_.empty() || std::find_if(sections_.begin(), sections_.end() - 1, section_ptr_finder(s)) != sections_.end() - 1)
+		throw pe_exception("Can't expand any section, except last one", pe_exception::error_expanding_section);
+
+	//Check if we should expand our section
+	if(expand == expand_section_raw && section_data_length_from_rva(s, needed_rva, section_data_raw) < needed_size)
+	{
+		//Expand section raw data
+		s.get_raw_data().resize(needed_rva - s.get_virtual_address() + needed_size);
+		recalculate_section_sizes(s, false);
+		return true;
+	}
+	else if(expand == expand_section_virtual && section_data_length_from_rva(s, needed_rva, section_data_virtual) < needed_size)
+	{
+		//Expand section virtual data
+		set_section_virtual_size(s, needed_rva - s.get_virtual_address() + needed_size);
+		return true;
+	}
+	
+	return false;
+}
+
+//Updates image virtual size
+void pe_base::update_image_size()
+{
+	//Write virtual size of image to headers
+	if(!sections_.empty())
+		set_size_of_image(sections_.back().get_virtual_address() + sections_.back().get_aligned_virtual_size(get_section_alignment()));
+	else
+		set_size_of_image(get_size_of_headers());
+}
+
+//Returns checksum of PE file from header
+uint32_t pe_base::get_checksum() const
+{
+	return props_->get_checksum();
+}
+
+//Sets checksum of PE file
+void pe_base::set_checksum(uint32_t checksum)
+{
+	props_->set_checksum(checksum);
+}
+
+//Returns timestamp of PE file from header
+uint32_t pe_base::get_time_date_stamp() const
+{
+	return props_->get_time_date_stamp();
+}
+
+//Sets timestamp of PE file
+void pe_base::set_time_date_stamp(uint32_t timestamp)
+{
+	props_->set_time_date_stamp(timestamp);
+}
+
+//Returns Machine field value of PE file from header
+uint16_t pe_base::get_machine() const
+{
+	return props_->get_machine();
+}
+
+//Sets Machine field value of PE file
+void pe_base::set_machine(uint16_t machine)
+{
+	props_->set_machine(machine);
+}
+
+//Prepares section before attaching it
+void pe_base::prepare_section(section& s)
+{
+	//Calculate its size of raw data
+	s.set_size_of_raw_data(static_cast<uint32_t>(pe_utils::align_up(s.get_raw_data().length(), get_file_alignment())));
+
+	//Check section virtual and raw size
+	if(!s.get_size_of_raw_data() && !s.get_virtual_size())
+		throw pe_exception("Virtual and Physical sizes of section can't be 0 at the same time", pe_exception::zero_section_sizes);
+
+	//If section virtual size is zero
+	if(!s.get_virtual_size())
+	{
+		s.set_virtual_size(s.get_size_of_raw_data());
+	}
+	else
+	{
+		//Else calculate its virtual size
+		s.set_virtual_size(
+			std::max<uint32_t>(pe_utils::align_up(s.get_size_of_raw_data(), get_file_alignment()),
+			pe_utils::align_up(s.get_virtual_size(), get_section_alignment())));
+	}
+}
+
+//Adds section to image
+section& pe_base::add_section(section s)
+{
+	if(sections_.size() >= maximum_number_of_sections)
+		throw pe_exception("Maximum number of sections has been reached", pe_exception::no_more_sections_can_be_added);
+
+	//Prepare section before adding it
+	prepare_section(s);
+
+	//Calculate section virtual address
+	if(!sections_.empty())
+	{
+		s.set_virtual_address(pe_utils::align_up(sections_.back().get_virtual_address() + sections_.back().get_aligned_virtual_size(get_section_alignment()), get_section_alignment()));
+
+		//We should align last section raw size, if it wasn't aligned
+		section& last = sections_.back();
+		last.set_size_of_raw_data(static_cast<uint32_t>(pe_utils::align_up(last.get_raw_data().length(), get_file_alignment())));
+	}
+	else
+	{
+		s.set_virtual_address(
+			s.get_virtual_address() == 0
+			? pe_utils::align_up(get_size_of_headers(), get_section_alignment())
+			: pe_utils::align_up(s.get_virtual_address(), get_section_alignment()));
+	}
+
+	//Add section to the end of section list
+	sections_.push_back(s);
+	//Set number of sections in PE header
+	set_number_of_sections(static_cast<uint16_t>(sections_.size()));
+	//Recalculate virtual size of image
+	set_size_of_image(get_size_of_image() + s.get_aligned_virtual_size(get_section_alignment()));
+	//rETurn last section
+	return sections_.back();
+}
+
+//Returns true if sectios "s" is already attached to this PE file
+bool pe_base::section_attached(const section& s) const
+{
+	return sections_.end() != std::find_if(sections_.begin(), sections_.end(), section_ptr_finder(s));
+}
+
+//Returns true if directory exists
+bool pe_base::directory_exists(uint32_t id) const
+{
+	return props_->directory_exists(id);
+}
+
+//Removes directory
+void pe_base::remove_directory(uint32_t id)
+{
+	props_->remove_directory(id);
+}
+
+//Returns directory RVA
+uint32_t pe_base::get_directory_rva(uint32_t id) const
+{
+	return props_->get_directory_rva(id);
+}
+
+//Returns directory size
+uint32_t pe_base::get_directory_size(uint32_t id) const
+{
+	return props_->get_directory_size(id);
+}
+
+//Sets directory RVA (just a value of PE header, no moving occurs)
+void pe_base::set_directory_rva(uint32_t id, uint32_t rva)
+{
+	return props_->set_directory_rva(id, rva);
+}
+
+//Sets directory size (just a value of PE header, no moving occurs)
+void pe_base::set_directory_size(uint32_t id, uint32_t size)
+{
+	return props_->set_directory_size(id, size);
+}
+
+//Strips only zero DATA_DIRECTORY entries to count = min_count
+//Returns resulting number of data directories
+//strip_iat_directory - if true, even not empty IAT directory will be stripped
+uint32_t pe_base::strip_data_directories(uint32_t min_count, bool strip_iat_directory)
+{
+	return props_->strip_data_directories(min_count, strip_iat_directory);
+}
+
+//Returns true if image has import directory
+bool pe_base::has_imports() const
+{
+	return directory_exists(image_directory_entry_import);
+}
+
+//Returns true if image has export directory
+bool pe_base::has_exports() const
+{
+	return directory_exists(image_directory_entry_export);
+}
+
+//Returns true if image has resource directory
+bool pe_base::has_resources() const
+{
+	return directory_exists(image_directory_entry_resource);
+}
+
+//Returns true if image has security directory
+bool pe_base::has_security() const
+{
+	return directory_exists(image_directory_entry_security);
+}
+
+//Returns true if image has relocations
+bool pe_base::has_reloc() const
+{
+	return directory_exists(image_directory_entry_basereloc) && !(get_characteristics() & image_file_relocs_stripped);
+}
+
+//Returns true if image has TLS directory
+bool pe_base::has_tls() const
+{
+	return directory_exists(image_directory_entry_tls);
+}
+
+//Returns true if image has config directory
+bool pe_base::has_config() const
+{
+	return directory_exists(image_directory_entry_load_config);
+}
+
+//Returns true if image has bound import directory
+bool pe_base::has_bound_import() const
+{
+	return directory_exists(image_directory_entry_bound_import);
+}
+
+//Returns true if image has delay import directory
+bool pe_base::has_delay_import() const
+{
+	return directory_exists(image_directory_entry_delay_import);
+}
+
+//Returns true if image has COM directory
+bool pe_base::is_dotnet() const
+{
+	return directory_exists(image_directory_entry_com_descriptor);
+}
+
+//Returns true if image has exception directory
+bool pe_base::has_exception_directory() const
+{
+	return directory_exists(image_directory_entry_exception);
+}
+
+//Returns true if image has debug directory
+bool pe_base::has_debug() const
+{
+	return directory_exists(image_directory_entry_debug);
+}
+
+//Returns corresponding section data pointer from RVA inside section "s" (checks bounds)
+char* pe_base::section_data_from_rva(section& s, uint32_t rva)
+{
+	//Check if RVA is inside section "s"
+	if(rva >= s.get_virtual_address() && rva < s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()))
+	{
+		if(s.get_raw_data().empty())
+			throw pe_exception("Section raw data is empty and cannot be changed", pe_exception::section_is_empty);
+
+		return &s.get_raw_data()[rva - s.get_virtual_address()];
+	}
+
+	throw pe_exception("RVA not found inside section", pe_exception::rva_not_exists);
+}
+
+//Returns corresponding section data pointer from RVA inside section "s" (checks bounds)
+const char* pe_base::section_data_from_rva(const section& s, uint32_t rva, section_data_type datatype) const
+{
+	//Check if RVA is inside section "s"
+	if(rva >= s.get_virtual_address() && rva < s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()))
+		return (datatype == section_data_raw ? s.get_raw_data().data() : s.get_virtual_data(get_section_alignment()).c_str()) + rva - s.get_virtual_address();
+
+	throw pe_exception("RVA not found inside section", pe_exception::rva_not_exists);
+}
+
+//Returns section TOTAL RAW/VIRTUAL data length from RVA inside section
+uint32_t pe_base::section_data_length_from_rva(uint32_t rva, section_data_type datatype, bool include_headers) const
+{
+	//if RVA is inside of headers and we're searching them too...
+	if(include_headers && rva < full_headers_data_.length())
+		return static_cast<unsigned long>(full_headers_data_.length());
+
+	const section& s = section_from_rva(rva);
+	return static_cast<unsigned long>(datatype == section_data_raw ? s.get_raw_data().length() /* instead of SizeOfRawData */ : s.get_aligned_virtual_size(get_section_alignment()));
+}
+
+//Returns section TOTAL RAW/VIRTUAL data length from VA inside section for PE32
+uint32_t pe_base::section_data_length_from_va(uint32_t va, section_data_type datatype, bool include_headers) const
+{
+	return section_data_length_from_rva(va_to_rva(va), datatype, include_headers);
+}
+
+//Returns section TOTAL RAW/VIRTUAL data length from VA inside section for PE32/PE64
+uint32_t pe_base::section_data_length_from_va(uint64_t va, section_data_type datatype, bool include_headers) const
+{
+	return section_data_length_from_rva(va_to_rva(va), datatype, include_headers);
+}
+
+//Returns section remaining RAW/VIRTUAL data length from RVA "rva_inside" to the end of section containing RVA "rva"
+uint32_t pe_base::section_data_length_from_rva(uint32_t rva, uint32_t rva_inside, section_data_type datatype, bool include_headers) const
+{
+	//if RVAs are inside of headers and we're searching them too...
+	if(include_headers && rva < full_headers_data_.length() && rva_inside < full_headers_data_.length())
+		return static_cast<unsigned long>(full_headers_data_.length() - rva_inside);
+
+	const section& s = section_from_rva(rva);
+	if(rva_inside < s.get_virtual_address())
+		throw pe_exception("RVA not found inside section", pe_exception::rva_not_exists);
+
+	//Calculate remaining length of section data from "rva" address
+	long length = static_cast<long>(datatype == section_data_raw ? s.get_raw_data().length() /* instead of SizeOfRawData */ : s.get_aligned_virtual_size(get_section_alignment()))
+		+ s.get_virtual_address() - rva_inside;
+
+	if(length < 0)
+		return 0;
+
+	return static_cast<unsigned long>(length);
+}
+
+//Returns section remaining RAW/VIRTUAL data length from VA "va_inside" to the end of section containing VA "va" for PE32
+uint32_t pe_base::section_data_length_from_va(uint32_t va, uint32_t va_inside, section_data_type datatype, bool include_headers) const
+{
+	return section_data_length_from_rva(va_to_rva(va), va_to_rva(va_inside), datatype, include_headers);
+}
+
+//Returns section remaining RAW/VIRTUAL data length from VA "va_inside" to the end of section containing VA "va" for PE32/PE64
+uint32_t pe_base::section_data_length_from_va(uint64_t va, uint64_t va_inside, section_data_type datatype, bool include_headers) const
+{
+	return section_data_length_from_rva(va_to_rva(va), va_to_rva(va_inside), datatype, include_headers);
+}
+
+//Returns section remaining RAW/VIRTUAL data length from RVA to the end of section "s" (checks bounds)
+uint32_t pe_base::section_data_length_from_rva(const section& s, uint32_t rva_inside, section_data_type datatype) const
+{
+	//Check rva_inside
+	if(rva_inside >= s.get_virtual_address() && rva_inside < s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()))
+	{
+		//Calculate remaining length of section data from "rva" address
+		int32_t length = static_cast<int32_t>(datatype == section_data_raw ? s.get_raw_data().length() /* instead of SizeOfRawData */ : s.get_aligned_virtual_size(get_section_alignment()))
+			+ s.get_virtual_address() - rva_inside;
+
+		if(length < 0)
+			return 0;
+
+		return static_cast<uint32_t>(length);
+	}
+
+	throw pe_exception("RVA not found inside section", pe_exception::rva_not_exists);
+}
+
+//Returns section remaining RAW/VIRTUAL data length from VA to the end of section "s" for PE32 (checks bounds)
+uint32_t pe_base::section_data_length_from_va(const section& s, uint32_t va_inside, section_data_type datatype) const
+{
+	return section_data_length_from_rva(s, va_to_rva(va_inside), datatype);
+}
+
+//Returns section remaining RAW/VIRTUAL data length from VA to the end of section "s" for PE32/PE64 (checks bounds)
+uint32_t pe_base::section_data_length_from_va(const section& s, uint64_t va_inside, section_data_type datatype) const
+{
+	return section_data_length_from_rva(s, va_to_rva(va_inside), datatype);
+}
+
+//Returns corresponding section data pointer from RVA inside section
+char* pe_base::section_data_from_rva(uint32_t rva, bool include_headers)
+{
+	//if RVA is inside of headers and we're searching them too...
+	if(include_headers && rva < full_headers_data_.length())
+		return &full_headers_data_[rva];
+
+	section& s = section_from_rva(rva);
+
+	if(s.get_raw_data().empty())
+		throw pe_exception("Section raw data is empty and cannot be changed", pe_exception::section_is_empty);
+
+	return &s.get_raw_data()[rva - s.get_virtual_address()];
+}
+
+//Returns corresponding section data pointer from RVA inside section
+const char* pe_base::section_data_from_rva(uint32_t rva, section_data_type datatype, bool include_headers) const
+{
+	//if RVA is inside of headers and we're searching them too...
+	if(include_headers && rva < full_headers_data_.length())
+		return &full_headers_data_[rva];
+
+	const section& s = section_from_rva(rva);
+	return (datatype == section_data_raw ? s.get_raw_data().data() : s.get_virtual_data(get_section_alignment()).c_str()) + rva - s.get_virtual_address();
+}
+
+//Reads DOS headers from istream
+void pe_base::read_dos_header(std::istream& file, image_dos_header& header)
+{
+	//Check istream flags
+	if(file.bad() || file.eof())
+		throw pe_exception("PE file stream is bad or closed.", pe_exception::bad_pe_file);
+
+	//Read DOS header and check istream
+	file.read(reinterpret_cast<char*>(&header), sizeof(image_dos_header));
+	if(file.bad() || file.eof())
+		throw pe_exception("Unable to read IMAGE_DOS_HEADER", pe_exception::bad_dos_header);
+
+	//Check DOS header magic
+	if(header.e_magic != 0x5a4d) //"MZ"
+		throw pe_exception("IMAGE_DOS_HEADER signature is incorrect", pe_exception::bad_dos_header);
+}
+
+//Reads DOS headers from istream
+void pe_base::read_dos_header(std::istream& file)
+{
+	read_dos_header(file, dos_header_);
+}
+
+//Reads PE image from istream
+void pe_base::read_pe(std::istream& file, bool read_debug_raw_data)
+{
+	//Get istream size
+	std::streamoff filesize = pe_utils::get_file_size(file);
+
+	//Check if PE header is DWORD-aligned
+	if((dos_header_.e_lfanew % sizeof(uint32_t)) != 0)
+		throw pe_exception("PE header is not DWORD-aligned", pe_exception::bad_dos_header);
+
+	//Seek to NT headers
+	file.seekg(dos_header_.e_lfanew);
+	if(file.bad() || file.fail())
+		throw pe_exception("Cannot reach IMAGE_NT_HEADERS", pe_exception::image_nt_headers_not_found);
+
+	//Read NT headers
+	file.read(get_nt_headers_ptr(), get_sizeof_nt_header() - sizeof(image_data_directory) * image_numberof_directory_entries);
+	if(file.bad() || file.eof())
+		throw pe_exception("Error reading IMAGE_NT_HEADERS", pe_exception::error_reading_image_nt_headers);
+
+	//Check PE signature
+	if(get_pe_signature() != 0x4550) //"PE"
+		throw pe_exception("Incorrect PE signature", pe_exception::pe_signature_incorrect);
+
+	//Check number of directories
+	if(get_number_of_rvas_and_sizes() > image_numberof_directory_entries)
+		set_number_of_rvas_and_sizes(image_numberof_directory_entries);
+
+	if(get_number_of_rvas_and_sizes() > 0)
+	{
+		//Read data directory headers, if any
+		file.read(get_nt_headers_ptr() + (get_sizeof_nt_header() - sizeof(image_data_directory) * image_numberof_directory_entries), sizeof(image_data_directory) * get_number_of_rvas_and_sizes());
+		if(file.bad() || file.eof())
+			throw pe_exception("Error reading DATA_DIRECTORY headers", pe_exception::error_reading_data_directories);
+	}
+
+	//Check section number
+	//Images with zero section number accepted
+	if(get_number_of_sections() > maximum_number_of_sections)
+		throw pe_exception("Incorrect number of sections", pe_exception::section_number_incorrect);
+
+	//Check PE magic
+	if(get_magic() != get_needed_magic())
+		throw pe_exception("Incorrect PE signature", pe_exception::pe_signature_incorrect);
+
+	//Check section alignment
+	if(!pe_utils::is_power_of_2(get_section_alignment()))
+		throw pe_exception("Incorrect section alignment", pe_exception::incorrect_section_alignment);
+
+	//Check file alignment
+	if(!pe_utils::is_power_of_2(get_file_alignment()))
+		throw pe_exception("Incorrect file alignment", pe_exception::incorrect_file_alignment);
+
+	if(get_file_alignment() != get_section_alignment() && (get_file_alignment() < minimum_file_alignment || get_file_alignment() > get_section_alignment()))
+		throw pe_exception("Incorrect file alignment", pe_exception::incorrect_file_alignment);
+
+	//Check size of image
+	if(pe_utils::align_up(get_size_of_image(), get_section_alignment()) == 0)
+		throw pe_exception("Incorrect size of image", pe_exception::incorrect_size_of_image);
+	
+	//Read rich data overlay / DOS stub (if any)
+	if(static_cast<uint32_t>(dos_header_.e_lfanew) > sizeof(image_dos_header))
+	{
+		rich_overlay_.resize(dos_header_.e_lfanew - sizeof(image_dos_header));
+		file.seekg(sizeof(image_dos_header));
+		file.read(&rich_overlay_[0], dos_header_.e_lfanew - sizeof(image_dos_header));
+		if(file.bad() || file.eof())
+			throw pe_exception("Error reading 'Rich' & 'DOS stub' overlay", pe_exception::error_reading_overlay);
+	}
+
+	//Calculate first section raw position
+	//Sum is safe here
+	uint32_t first_section = dos_header_.e_lfanew + get_size_of_optional_header() + sizeof(image_file_header) + sizeof(uint32_t) /* Signature */;
+
+	if(get_number_of_sections() > 0)
+	{
+		//Go to first section
+		file.seekg(first_section);
+		if(file.bad() || file.fail())
+			throw pe_exception("Cannot reach section headers", pe_exception::image_section_headers_not_found);
+	}
+
+	uint32_t last_raw_size = 0;
+
+	//Read all sections
+	for(int i = 0; i < get_number_of_sections(); i++)
+	{
+		section s;
+		//Read section header
+		file.read(reinterpret_cast<char*>(&s.get_raw_header()), sizeof(image_section_header));
+		if(file.bad() || file.eof())
+			throw pe_exception("Error reading section header", pe_exception::error_reading_section_header);
+
+		//Save next section header position
+		std::streamoff next_sect = file.tellg();
+
+		//Check section virtual and raw sizes
+		if(!s.get_size_of_raw_data() && !s.get_virtual_size())
+			throw pe_exception("Virtual and Physical sizes of section can't be 0 at the same time", pe_exception::zero_section_sizes);
+
+		//Check for adequate values of section fields
+		if(!pe_utils::is_sum_safe(s.get_virtual_address(), s.get_virtual_size()) || s.get_virtual_size() > pe_utils::two_gb
+			|| !pe_utils::is_sum_safe(s.get_pointer_to_raw_data(), s.get_size_of_raw_data()) || s.get_size_of_raw_data() > pe_utils::two_gb)
+			throw pe_exception("Incorrect section address or size", pe_exception::section_incorrect_addr_or_size);
+
+		if(s.get_size_of_raw_data() != 0)
+		{
+			//If section has raw data
+
+			//If section raw data size is greater than virtual, fix it
+			last_raw_size = s.get_size_of_raw_data();
+			if(pe_utils::align_up(s.get_size_of_raw_data(), get_file_alignment()) > pe_utils::align_up(s.get_virtual_size(), get_section_alignment()))
+				s.set_size_of_raw_data(s.get_virtual_size());
+
+			//Check virtual and raw section sizes and addresses
+			if(s.get_virtual_address() + pe_utils::align_up(s.get_virtual_size(), get_section_alignment()) > pe_utils::align_up(get_size_of_image(), get_section_alignment())
+				||
+				pe_utils::align_down(s.get_pointer_to_raw_data(), get_file_alignment()) + s.get_size_of_raw_data() > static_cast<uint32_t>(filesize))
+				throw pe_exception("Incorrect section address or size", pe_exception::section_incorrect_addr_or_size);
+
+			//Seek to section raw data
+			file.seekg(pe_utils::align_down(s.get_pointer_to_raw_data(), get_file_alignment()));
+			if(file.bad() || file.fail())
+				throw pe_exception("Cannot reach section data", pe_exception::image_section_data_not_found);
+
+			//Read section raw data
+			s.get_raw_data().resize(s.get_size_of_raw_data());
+			file.read(&s.get_raw_data()[0], s.get_size_of_raw_data());
+			if(file.bad() || file.fail())
+				throw pe_exception("Error reading section data", pe_exception::image_section_data_not_found);
+		}
+
+		//Check virtual address and size of section
+		if(s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()) > pe_utils::align_up(get_size_of_image(), get_section_alignment()))
+			throw pe_exception("Incorrect section address or size", pe_exception::section_incorrect_addr_or_size);
+
+		//Save section
+		sections_.push_back(s);
+
+		//Seek to the next section header
+		file.seekg(next_sect);
+	}
+
+	//Check size of headers: SizeOfHeaders can't be larger than first section VA
+	if(!sections_.empty() && get_size_of_headers() > sections_.front().get_virtual_address())
+		throw pe_exception("Incorrect size of headers", pe_exception::incorrect_size_of_headers);
+
+	//If image has more than two sections
+	if(sections_.size() >= 2)
+	{
+		//Check sections virtual sizes
+		for(section_list::const_iterator i = sections_.begin() + 1; i != sections_.end(); ++i)
+		{
+			if((*i).get_virtual_address() != (*(i - 1)).get_virtual_address() + (*(i - 1)).get_aligned_virtual_size(get_section_alignment()))
+				throw pe_exception("Section table is incorrect", pe_exception::image_section_table_incorrect);
+		}
+	}
+
+	//Check if image has overlay in the end of file
+	has_overlay_ = !sections_.empty() && filesize > static_cast<std::streamoff>(sections_.back().get_pointer_to_raw_data() + last_raw_size);
+
+	{
+		//Additionally, read data from the beginning of istream to size of headers
+		file.seekg(0);
+		uint32_t size_of_headers = std::min<uint32_t>(get_size_of_headers(), static_cast<uint32_t>(filesize));
+
+		if(!sections_.empty())
+		{
+			for(section_list::const_iterator i = sections_.begin(); i != sections_.end(); ++i)
+			{
+				if(!(*i).empty())
+				{
+					size_of_headers = std::min<uint32_t>(get_size_of_headers(), (*i).get_pointer_to_raw_data());
+					break;
+				}
+			}
+		}
+
+		full_headers_data_.resize(size_of_headers);
+		file.read(&full_headers_data_[0], size_of_headers);
+		if(file.bad() || file.eof())
+			throw pe_exception("Error reading file", pe_exception::error_reading_file);
+	}
+
+	//Moreover, if there's debug directory, read its raw data for some debug info types
+	while(read_debug_raw_data && has_debug())
+	{
+		try
+		{
+			//Check the length in bytes of the section containing debug directory
+			if(section_data_length_from_rva(get_directory_rva(image_directory_entry_debug), get_directory_rva(image_directory_entry_debug), section_data_virtual, true) < sizeof(image_debug_directory))
+				break;
+
+			unsigned long current_pos = get_directory_rva(image_directory_entry_debug);
+
+			//First IMAGE_DEBUG_DIRECTORY table
+			image_debug_directory directory = section_data_from_rva<image_debug_directory>(current_pos, section_data_virtual, true);
+
+			//Iterate over all IMAGE_DEBUG_DIRECTORY directories
+			while(directory.PointerToRawData
+				&& current_pos < get_directory_rva(image_directory_entry_debug) + get_directory_size(image_directory_entry_debug))
+			{
+				//If we have something to read
+				if((directory.Type == image_debug_type_codeview
+					|| directory.Type == image_debug_type_misc
+					|| directory.Type == image_debug_type_coff)
+					&& directory.SizeOfData)
+				{
+					std::string data;
+					data.resize(directory.SizeOfData);
+					file.seekg(directory.PointerToRawData);
+					file.read(&data[0], directory.SizeOfData);
+					if(file.bad() || file.eof())
+						throw pe_exception("Error reading file", pe_exception::error_reading_file);
+
+					debug_data_.insert(std::make_pair(directory.PointerToRawData, data));
+				}
+
+				//Go to next debug entry
+				current_pos += sizeof(image_debug_directory);
+				directory = section_data_from_rva<image_debug_directory>(current_pos, section_data_virtual, true);
+			}
+
+			break;
+		}
+		catch(const pe_exception&)
+		{
+			//Don't throw any exception here, if debug info is corrupted or incorrect
+			break;
+		}
+		catch(const std::bad_alloc&)
+		{
+			//Don't throw any exception here, if debug info is corrupted or incorrect
+			break;
+		}
+	}
+}
+
+//Returns PE type of this image
+pe_type pe_base::get_pe_type() const
+{
+	return props_->get_pe_type();
+}
+
+//Returns PE type (PE or PE+) from pe_type enumeration (minimal correctness checks)
+pe_type pe_base::get_pe_type(std::istream& file)
+{
+	//Save state of the istream
+	std::ios_base::iostate state = file.exceptions();
+	std::streamoff old_offset = file.tellg();
+	image_nt_headers32 nt_headers;
+	image_dos_header header;
+
+	try
+	{
+		//Read dos header
+		file.exceptions(std::ios::goodbit);
+		read_dos_header(file, header);
+
+		//Seek to the NT headers start
+		file.seekg(header.e_lfanew);
+		if(file.bad() || file.fail())
+			throw pe_exception("Cannot reach IMAGE_NT_HEADERS", pe_exception::image_nt_headers_not_found);
+
+		//Read NT headers (we're using 32-bit version, because there's no significant differencies between 32 and 64 bit version structures)
+		file.read(reinterpret_cast<char*>(&nt_headers), sizeof(image_nt_headers32) - sizeof(image_data_directory) * image_numberof_directory_entries);
+		if(file.bad() || file.eof())
+			throw pe_exception("Error reading IMAGE_NT_HEADERS", pe_exception::error_reading_image_nt_headers);
+
+		//Check NT headers signature
+		if(nt_headers.Signature != 0x4550) //"PE"
+			throw pe_exception("Incorrect PE signature", pe_exception::pe_signature_incorrect);
+
+		//Check NT headers magic
+		if(nt_headers.OptionalHeader.Magic != image_nt_optional_hdr32_magic && nt_headers.OptionalHeader.Magic != image_nt_optional_hdr64_magic)
+			throw pe_exception("Incorrect PE signature", pe_exception::pe_signature_incorrect);
+	}
+	catch(const std::exception&)
+	{
+		//If something went wrong, restore istream state
+		file.exceptions(state);
+		file.seekg(old_offset);
+		file.clear();
+		//Retrhow exception
+		throw;
+	}
+
+	//Restore stream state
+	file.exceptions(state);
+	file.seekg(old_offset);
+	file.clear();
+
+	//Determine PE type and return it
+	return nt_headers.OptionalHeader.Magic == image_nt_optional_hdr64_magic ? pe_type_64 : pe_type_32;
+}
+
+//Returns true if image has overlay data at the end of file
+bool pe_base::has_overlay() const
+{
+	return has_overlay_;
+}
+
+//Clears PE characteristics flag
+void pe_base::clear_characteristics_flags(uint16_t flags)
+{
+	set_characteristics(get_characteristics() & ~flags);
+}
+
+//Sets PE characteristics flag
+void pe_base::set_characteristics_flags(uint16_t flags)
+{
+	set_characteristics(get_characteristics() | flags);
+}
+
+//Returns true if PE characteristics flag set
+bool pe_base::check_characteristics_flag(uint16_t flag) const
+{
+	return (get_characteristics() & flag) ? true : false;
+}
+
+//Returns subsystem value
+uint16_t pe_base::get_subsystem() const
+{
+	return props_->get_subsystem();
+}
+
+//Sets subsystem value
+void pe_base::set_subsystem(uint16_t subsystem)
+{
+	props_->set_subsystem(subsystem);
+}
+
+//Returns true if image has console subsystem
+bool pe_base::is_console() const
+{
+	return get_subsystem() == image_subsystem_windows_cui;
+}
+
+//Returns true if image has Windows GUI subsystem
+bool pe_base::is_gui() const
+{
+	return get_subsystem() == image_subsystem_windows_gui;
+}
+
+//Sets required operation system version
+void pe_base::set_os_version(uint16_t major, uint16_t minor)
+{
+	props_->set_os_version(major, minor);
+}
+
+//Returns required operation system version (minor word)
+uint16_t pe_base::get_minor_os_version() const
+{
+	return props_->get_minor_os_version();
+}
+
+//Returns required operation system version (major word)
+uint16_t pe_base::get_major_os_version() const
+{
+	return props_->get_major_os_version();
+}
+
+//Sets required subsystem version
+void pe_base::set_subsystem_version(uint16_t major, uint16_t minor)
+{
+	props_->set_subsystem_version(major, minor);
+}
+
+//Returns required subsystem version (minor word)
+uint16_t pe_base::get_minor_subsystem_version() const
+{
+	return props_->get_minor_subsystem_version();
+}
+
+//Returns required subsystem version (major word)
+uint16_t pe_base::get_major_subsystem_version() const
+{
+	return props_->get_major_subsystem_version();
+}
+
+//Returns corresponding section data pointer from VA inside section "s" for PE32 (checks bounds)
+char* pe_base::section_data_from_va(section& s, uint32_t va) //Always returns raw data
+{
+	return section_data_from_rva(s, va_to_rva(va));
+}
+
+//Returns corresponding section data pointer from VA inside section "s" for PE32 (checks bounds)
+const char* pe_base::section_data_from_va(const section& s, uint32_t va, section_data_type datatype) const
+{
+	return section_data_from_rva(s, va_to_rva(va), datatype);
+}
+
+//Returns corresponding section data pointer from VA inside section for PE32
+char* pe_base::section_data_from_va(uint32_t va, bool include_headers) //Always returns raw data
+{
+	return section_data_from_rva(va_to_rva(va), include_headers);
+}
+
+//Returns corresponding section data pointer from VA inside section for PE32
+const char* pe_base::section_data_from_va(uint32_t va, section_data_type datatype, bool include_headers) const
+{
+	return section_data_from_rva(va_to_rva(va), datatype, include_headers);
+}
+
+//Returns corresponding section data pointer from VA inside section "s" for PE32/PE64 (checks bounds)
+char* pe_base::section_data_from_va(section& s, uint64_t va)  //Always returns raw data
+{
+	return section_data_from_rva(s, va_to_rva(va));
+}
+
+//Returns corresponding section data pointer from VA inside section "s" for PE32/PE64 (checks bounds)
+const char* pe_base::section_data_from_va(const section& s, uint64_t va, section_data_type datatype) const
+{
+	return section_data_from_rva(s, va_to_rva(va), datatype);
+}
+
+//Returns corresponding section data pointer from VA inside section for PE32/PE64
+char* pe_base::section_data_from_va(uint64_t va, bool include_headers)  //Always returns raw data
+{
+	return section_data_from_rva(va_to_rva(va), include_headers);
+}
+
+//Returns corresponding section data pointer from VA inside section for PE32/PE64
+const char* pe_base::section_data_from_va(uint64_t va, section_data_type datatype, bool include_headers) const
+{
+	return section_data_from_rva(va_to_rva(va), datatype, include_headers);
+}
+
+//Returns section from VA inside it for PE32
+section& pe_base::section_from_va(uint32_t va)
+{
+	return section_from_rva(va_to_rva(va));
+}
+
+//Returns section from VA inside it for PE32/PE64
+section& pe_base::section_from_va(uint64_t va)
+{
+	return section_from_rva(va_to_rva(va));
+}
+
+//Returns section from RVA inside it for PE32
+const section& pe_base::section_from_va(uint32_t va) const
+{
+	return section_from_rva(va_to_rva(va));
+}
+
+//Returns section from RVA inside it for PE32/PE64
+const section& pe_base::section_from_va(uint64_t va) const
+{
+	return section_from_rva(va_to_rva(va));
+}
+
+uint32_t pe_base::va_to_rva(uint32_t va, bool bound_check) const
+{
+	return props_->va_to_rva(va, bound_check);
+}
+
+uint32_t pe_base::va_to_rva(uint64_t va, bool bound_check) const
+{
+	return props_->va_to_rva(va, bound_check);
+}
+
+uint32_t pe_base::rva_to_va_32(uint32_t rva) const
+{
+	return props_->rva_to_va_32(rva);
+}
+
+uint64_t pe_base::rva_to_va_64(uint32_t rva) const
+{
+	return props_->rva_to_va_64(rva);
+}
+
+//Relative Virtual Address (RVA) to Virtual Address (VA) convertion for PE32
+void pe_base::rva_to_va(uint32_t rva, uint32_t& va) const
+{
+	va = rva_to_va_32(rva);
+}
+
+//Relative Virtual Address (RVA) to Virtual Address (VA) convertions for PE32/PE64
+void pe_base::rva_to_va(uint32_t rva, uint64_t& va) const
+{
+	va = rva_to_va_64(rva);
+}
+
+//Returns section from file offset (4gb max)
+section& pe_base::section_from_file_offset(uint32_t offset)
+{
+	return *file_offset_to_section(offset);
+}
+
+//Returns section from file offset (4gb max)
+const section& pe_base::section_from_file_offset(uint32_t offset) const
+{
+	return *file_offset_to_section(offset);
+}
+
+//Returns section and offset (raw data only) from its start from RVA
+const std::pair<uint32_t, const section*> pe_base::section_and_offset_from_rva(uint32_t rva) const
+{
+	const section& s = section_from_rva(rva);
+	return std::make_pair(rva - s.get_virtual_address(), &s);
+}
+
+//Returns DLL Characteristics
+uint16_t pe_base::get_dll_characteristics() const
+{
+	return props_->get_dll_characteristics();
+}
+
+//Sets DLL Characteristics
+void pe_base::set_dll_characteristics(uint16_t characteristics)
+{
+	props_->set_dll_characteristics(characteristics);
+}
+
+//Returns size of headers
+uint32_t pe_base::get_size_of_headers() const
+{
+	return props_->get_size_of_headers();
+}
+
+//Returns size of optional header
+uint16_t pe_base::get_size_of_optional_header() const
+{
+	return props_->get_size_of_optional_header();
+}
+
+//Returns PE signature
+uint32_t pe_base::get_pe_signature() const
+{
+	return props_->get_pe_signature();
+}
+
+//Returns magic value
+uint32_t pe_base::get_magic() const
+{
+	return props_->get_magic();
+}
+
+//Returns image base for PE32
+void pe_base::get_image_base(uint32_t& base) const
+{
+	base = get_image_base_32();
+}
+
+//Returns image base for PE32 and PE64 respectively
+uint32_t pe_base::get_image_base_32() const
+{
+	return props_->get_image_base_32();
+}
+
+//Sets image base for PE32 and PE64 respectively
+uint64_t pe_base::get_image_base_64() const
+{
+	return props_->get_image_base_64();
+}
+
+//RVA to RAW file offset convertion (4gb max)
+uint32_t pe_base::rva_to_file_offset(uint32_t rva) const
+{
+	//Maybe, RVA is inside PE headers
+	if(rva < get_size_of_headers())
+		return rva;
+
+	const section& s = section_from_rva(rva);
+	return s.get_pointer_to_raw_data() + rva - s.get_virtual_address();
+}
+
+//RAW file offset to RVA convertion (4gb max)
+uint32_t pe_base::file_offset_to_rva(uint32_t offset) const
+{
+	//Maybe, offset is inside PE headers
+	if(offset < get_size_of_headers())
+		return offset;
+
+	const section_list::const_iterator it = file_offset_to_section(offset);
+	return offset - (*it).get_pointer_to_raw_data() + (*it).get_virtual_address();
+}
+
+//RAW file offset to section convertion helper (4gb max)
+section_list::const_iterator pe_base::file_offset_to_section(uint32_t offset) const
+{
+	section_list::const_iterator it = std::find_if(sections_.begin(), sections_.end(), section_by_raw_offset(offset));
+	if(it == sections_.end())
+		throw pe_exception("No section found by presented file offset", pe_exception::no_section_found);
+
+	return it;
+}
+
+//RAW file offset to section convertion helper (4gb max)
+section_list::iterator pe_base::file_offset_to_section(uint32_t offset)
+{
+	section_list::iterator it = std::find_if(sections_.begin(), sections_.end(), section_by_raw_offset(offset));
+	if(it == sections_.end())
+		throw pe_exception("No section found by presented file offset", pe_exception::no_section_found);
+	
+	return it;
+}
+
+//RVA from section raw data offset
+uint32_t pe_base::rva_from_section_offset(const section& s, uint32_t raw_offset_from_section_start)
+{
+	return s.get_virtual_address() + raw_offset_from_section_start;
+}
+
+//Returns image base for PE32/PE64
+void pe_base::get_image_base(uint64_t& base) const
+{
+	base = get_image_base_64();
+}
+
+//Sets new image base
+void pe_base::set_image_base(uint32_t base)
+{
+	props_->set_image_base(base);
+}
+
+void pe_base::set_image_base_64(uint64_t base)
+{
+	props_->set_image_base_64(base);
+}
+
+//Sets heap size commit for PE32 and PE64 respectively
+void pe_base::set_heap_size_commit(uint32_t size)
+{
+	props_->set_heap_size_commit(size);
+}
+
+void pe_base::set_heap_size_commit(uint64_t size)
+{
+	props_->set_heap_size_commit(size);
+}
+
+//Sets heap size reserve for PE32 and PE64 respectively
+void pe_base::set_heap_size_reserve(uint32_t size)
+{
+	props_->set_heap_size_reserve(size);
+}
+
+void pe_base::set_heap_size_reserve(uint64_t size)
+{
+	props_->set_heap_size_reserve(size);
+}
+
+//Sets stack size commit for PE32 and PE64 respectively
+void pe_base::set_stack_size_commit(uint32_t size)
+{
+	props_->set_stack_size_commit(size);
+}
+
+void pe_base::set_stack_size_commit(uint64_t size)
+{
+	props_->set_stack_size_commit(size);
+}
+
+//Sets stack size reserve for PE32 and PE64 respectively
+void pe_base::set_stack_size_reserve(uint32_t size)
+{
+	props_->set_stack_size_reserve(size);
+}
+
+void pe_base::set_stack_size_reserve(uint64_t size)
+{
+	props_->set_stack_size_reserve(size);
+}
+
+//Returns heap size commit for PE32 and PE64 respectively
+uint32_t pe_base::get_heap_size_commit_32() const
+{
+	return props_->get_heap_size_commit_32();
+}
+
+uint64_t pe_base::get_heap_size_commit_64() const
+{
+	return props_->get_heap_size_commit_64();
+}
+
+//Returns heap size reserve for PE32 and PE64 respectively
+uint32_t pe_base::get_heap_size_reserve_32() const
+{
+	return props_->get_heap_size_reserve_32();
+}
+
+uint64_t pe_base::get_heap_size_reserve_64() const
+{
+	return props_->get_heap_size_reserve_64();
+}
+
+//Returns stack size commit for PE32 and PE64 respectively
+uint32_t pe_base::get_stack_size_commit_32() const
+{
+	return props_->get_stack_size_commit_32();
+}
+
+uint64_t pe_base::get_stack_size_commit_64() const
+{
+	return props_->get_stack_size_commit_64();
+}
+
+//Returns stack size reserve for PE32 and PE64 respectively
+uint32_t pe_base::get_stack_size_reserve_32() const
+{
+	return props_->get_stack_size_reserve_32();
+}
+
+uint64_t pe_base::get_stack_size_reserve_64() const
+{
+	return props_->get_stack_size_reserve_64();
+}
+
+//Returns heap size commit for PE32
+void pe_base::get_heap_size_commit(uint32_t& size) const
+{
+	size = get_heap_size_commit_32();
+}
+
+//Returns heap size commit for PE32/PE64
+void pe_base::get_heap_size_commit(uint64_t& size) const
+{
+	size = get_heap_size_commit_64();
+}
+
+//Returns heap size reserve for PE32
+void pe_base::get_heap_size_reserve(uint32_t& size) const
+{
+	size = get_heap_size_reserve_32();
+}
+
+//Returns heap size reserve for PE32/PE64
+void pe_base::get_heap_size_reserve(uint64_t& size) const
+{
+	size = get_heap_size_reserve_64();
+}
+
+//Returns stack size commit for PE32
+void pe_base::get_stack_size_commit(uint32_t& size) const
+{
+	size = get_stack_size_commit_32();
+}
+
+//Returns stack size commit for PE32/PE64
+void pe_base::get_stack_size_commit(uint64_t& size) const
+{
+	size = get_stack_size_commit_64();
+}
+
+//Returns stack size reserve for PE32
+void pe_base::get_stack_size_reserve(uint32_t& size) const
+{
+	size = get_stack_size_reserve_32();
+}
+
+//Returns stack size reserve for PE32/PE64
+void pe_base::get_stack_size_reserve(uint64_t& size) const
+{
+	size = get_stack_size_reserve_64();
+}
+
+//Realigns file (changes file alignment)
+void pe_base::realign_file(uint32_t new_file_alignment)
+{
+	//Checks alignment for correctness
+	set_file_alignment(new_file_alignment);
+	realign_all_sections();
+}
+
+//Helper function to recalculate RAW and virtual section sizes and strip it, if necessary
+void pe_base::recalculate_section_sizes(section& s, bool auto_strip)
+{
+	prepare_section(s); //Recalculate section raw addresses
+
+	//Strip RAW size of section, if it is the last one
+	//For all others it must be file-aligned and calculated by prepare_section() call
+	if(auto_strip && !(sections_.empty() || &s == &*(sections_.end() - 1)))
+	{
+		//Strip ending raw data nullbytes to optimize size
+		std::string& raw_data = s.get_raw_data();
+		if(!raw_data.empty())
+		{
+			std::string::size_type i = raw_data.length();
+			for(; i != 1; --i)
+			{
+				if(raw_data[i - 1] != 0)
+					break;
+			}
+			
+			raw_data.resize(i);
+		}
+
+		s.set_size_of_raw_data(static_cast<uint32_t>(raw_data.length()));
+	}
+
+	//Can occur only for last section
+	if(pe_utils::align_up(s.get_virtual_size(), get_section_alignment()) < pe_utils::align_up(s.get_size_of_raw_data(), get_file_alignment()))
+		set_section_virtual_size(s, pe_utils::align_up(s.get_size_of_raw_data(), get_section_alignment())); //Recalculate section virtual size
+}
+
+//Returns data from the beginning of image
+//Size = SizeOfHeaders
+const std::string& pe_base::get_full_headers_data() const
+{
+	return full_headers_data_;
+}
+
+const pe_base::debug_data_list& pe_base::get_raw_debug_data_list() const
+{
+	return debug_data_;
+}
+
+//Sets number of sections
+void pe_base::set_number_of_sections(uint16_t number)
+{
+	props_->set_number_of_sections(number);
+}
+
+//Sets size of image
+void pe_base::set_size_of_image(uint32_t size)
+{
+	props_->set_size_of_image(size);
+}
+
+//Sets size of headers
+void pe_base::set_size_of_headers(uint32_t size)
+{
+	props_->set_size_of_headers(size);
+}
+
+//Sets size of optional headers
+void pe_base::set_size_of_optional_header(uint16_t size)
+{
+	props_->set_size_of_optional_header(size);
+}
+
+//Returns nt headers data pointer
+char* pe_base::get_nt_headers_ptr()
+{
+	return props_->get_nt_headers_ptr();
+}
+
+//Returns nt headers data pointer
+const char* pe_base::get_nt_headers_ptr() const
+{
+	return props_->get_nt_headers_ptr();
+}
+
+//Returns sizeof() nt headers
+uint32_t pe_base::get_sizeof_nt_header() const
+{
+	return props_->get_sizeof_nt_header();
+}
+
+//Returns sizeof() optional headers
+uint32_t pe_base::get_sizeof_opt_headers() const
+{
+	return props_->get_sizeof_opt_headers();
+}
+
+//Sets file alignment (no checks)
+void pe_base::set_file_alignment_unchecked(uint32_t alignment)
+{
+	props_->set_file_alignment_unchecked(alignment);
+}
+
+//Sets base of code
+void pe_base::set_base_of_code(uint32_t base)
+{
+	props_->set_base_of_code(base);
+}
+
+//Returns base of code
+uint32_t pe_base::get_base_of_code() const
+{
+	return props_->get_base_of_code();
+}
+
+//Returns needed magic of image
+uint32_t pe_base::get_needed_magic() const
+{
+	return props_->get_needed_magic();
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_base.h b/irdb-lib/pebliss/trunk/pe_lib/pe_base.h
new file mode 100644
index 0000000000000000000000000000000000000000..334914e662989d219728b8a0bd4d241381cc75ef
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_base.h
@@ -0,0 +1,530 @@
+#ifndef pebliss_pe_base_h
+#define pebliss_pe_base_h
+#pragma once
+#ifndef pebliss_pebase_h
+#define pebliss_pebase_h
+
+#include <string>
+#include <vector>
+#include <istream>
+#include <ostream>
+#include <map>
+#include "pe_exception.h"
+#include "pe_structures.h"
+#include "utils.h"
+#include "pe_section.h"
+#include "pe_properties.h"
+
+//Please don't remove this information from header
+//PEBliss 1.0.0
+//(c) DX 2011 - 2012, http://kaimi.ru
+//Free to use for commertial and non-commertial purposes, modification and distribution
+
+// == more important ==
+//TODO: compact import rebuilder
+//TODO: remove sections in the middle
+//== less important ==
+//TODO: relocations that take more than one element (seems to be not possible in Windows PE, but anyway)
+//TODO: delay import directory
+//TODO: write message tables
+//TODO: write string tables
+//TODO: read security information
+//TODO: read full .NET information
+
+namespace pe_bliss
+{
+//Portable executable class
+class pe_base
+{
+public: //CONSTRUCTORS
+	//Constructor from stream
+	pe_base(std::istream& file, const pe_properties& props, bool read_debug_raw_data = true);
+
+	//Constructor of empty PE-file
+	explicit pe_base(const pe_properties& props, uint32_t section_alignment = 0x1000, bool dll = false, uint16_t subsystem = pe_win::image_subsystem_windows_gui);
+
+	pe_base(const pe_base& pe);
+	pe_base& operator=(const pe_base& pe);
+
+public:
+	~pe_base();
+
+public: //STUB
+	//Strips stub MSVS overlay, if any
+	void strip_stub_overlay();
+	//Fills stub MSVS overlay with specified byte
+	void fill_stub_overlay(char c);
+	//Sets stub MSVS overlay
+	void set_stub_overlay(const std::string& data);
+	//Returns stub overlay contents
+	const std::string& get_stub_overlay() const;
+
+
+public: //DIRECTORIES
+	//Returns true if directory exists
+	bool directory_exists(uint32_t id) const;
+	//Removes directory
+	void remove_directory(uint32_t id);
+
+	//Returns directory RVA
+	uint32_t get_directory_rva(uint32_t id) const;
+	//Returns directory size
+	uint32_t get_directory_size(uint32_t id) const;
+
+	//Sets directory RVA (just a value of PE header, no moving occurs)
+	void set_directory_rva(uint32_t id, uint32_t rva);
+	//Sets directory size (just a value of PE header, no moving occurs)
+	void set_directory_size(uint32_t id, uint32_t size);
+
+	//Strips only zero DATA_DIRECTORY entries to count = min_count
+	//Returns resulting number of data directories
+	//strip_iat_directory - if true, even not empty IAT directory will be stripped
+	uint32_t strip_data_directories(uint32_t min_count = 1, bool strip_iat_directory = true);
+
+	//Returns true if image has import directory
+	bool has_imports() const;
+	//Returns true if image has export directory
+	bool has_exports() const;
+	//Returns true if image has resource directory
+	bool has_resources() const;
+	//Returns true if image has security directory
+	bool has_security() const;
+	//Returns true if image has relocations
+	bool has_reloc() const;
+	//Returns true if image has TLS directory
+	bool has_tls() const;
+	//Returns true if image has config directory
+	bool has_config() const;
+	//Returns true if image has bound import directory
+	bool has_bound_import() const;
+	//Returns true if image has delay import directory
+	bool has_delay_import() const;
+	//Returns true if image has COM directory
+	bool is_dotnet() const;
+	//Returns true if image has exception directory
+	bool has_exception_directory() const;
+	//Returns true if image has debug directory
+	bool has_debug() const;
+
+	//Returns subsystem value
+	uint16_t get_subsystem() const;
+	//Sets subsystem value
+	void set_subsystem(uint16_t subsystem);
+	//Returns true if image has console subsystem
+	bool is_console() const;
+	//Returns true if image has Windows GUI subsystem
+	bool is_gui() const;
+
+	//Sets required operation system version
+	void set_os_version(uint16_t major, uint16_t minor);
+	//Returns required operation system version (minor word)
+	uint16_t get_minor_os_version() const;
+	//Returns required operation system version (major word)
+	uint16_t get_major_os_version() const;
+
+	//Sets required subsystem version
+	void set_subsystem_version(uint16_t major, uint16_t minor);
+	//Returns required subsystem version (minor word)
+	uint16_t get_minor_subsystem_version() const;
+	//Returns required subsystem version (major word)
+	uint16_t get_major_subsystem_version() const;
+
+public: //PE HEADER
+	//Returns DOS header
+	const pe_win::image_dos_header& get_dos_header() const;
+	pe_win::image_dos_header& get_dos_header();
+
+	//Returns PE header start (e_lfanew)
+	int32_t get_pe_header_start() const;
+
+	//Returns file alignment
+	uint32_t get_file_alignment() const;
+	//Sets file alignment, checking the correctness of its value
+	void set_file_alignment(uint32_t alignment);
+
+	//Returns size of image
+	uint32_t get_size_of_image() const;
+
+	//Returns image entry point
+	uint32_t get_ep() const;
+	//Sets image entry point (just a value of PE header)
+	void set_ep(uint32_t new_ep);
+
+	//Returns number of RVA and sizes (number of DATA_DIRECTORY entries)
+	uint32_t get_number_of_rvas_and_sizes() const;
+	//Sets number of RVA and sizes (number of DATA_DIRECTORY entries)
+	void set_number_of_rvas_and_sizes(uint32_t number);
+
+	//Returns PE characteristics
+	uint16_t get_characteristics() const;
+	//Sets PE characteristics (a value inside header)
+	void set_characteristics(uint16_t ch);
+	//Clears PE characteristics flag
+	void clear_characteristics_flags(uint16_t flags);
+	//Sets PE characteristics flag
+	void set_characteristics_flags(uint16_t flags);
+	//Returns true if PE characteristics flag set
+	bool check_characteristics_flag(uint16_t flag) const;
+	
+	//Returns DLL Characteristics
+	uint16_t get_dll_characteristics() const;
+	//Sets DLL Characteristics
+	void set_dll_characteristics(uint16_t characteristics);
+
+	//Returns size of headers
+	uint32_t get_size_of_headers() const;
+	//Returns size of optional header
+	uint16_t get_size_of_optional_header() const;
+
+	//Returns PE signature
+	uint32_t get_pe_signature() const;
+
+	//Returns magic value
+	uint32_t get_magic() const;
+
+	//Returns image base for PE32 and PE64 respectively
+	uint32_t get_image_base_32() const;
+	void get_image_base(uint32_t& base) const;
+	//Sets image base for PE32 and PE64 respectively
+	uint64_t get_image_base_64() const;
+	void get_image_base(uint64_t& base) const;
+
+	//Sets new image base
+	void set_image_base(uint32_t base);
+	void set_image_base_64(uint64_t base);
+
+	//Sets heap size commit for PE32 and PE64 respectively
+	void set_heap_size_commit(uint32_t size);
+	void set_heap_size_commit(uint64_t size);
+	//Sets heap size reserve for PE32 and PE64 respectively
+	void set_heap_size_reserve(uint32_t size);
+	void set_heap_size_reserve(uint64_t size);
+	//Sets stack size commit for PE32 and PE64 respectively
+	void set_stack_size_commit(uint32_t size);
+	void set_stack_size_commit(uint64_t size);
+	//Sets stack size reserve for PE32 and PE64 respectively
+	void set_stack_size_reserve(uint32_t size);
+	void set_stack_size_reserve(uint64_t size);
+
+	//Returns heap size commit for PE32 and PE64 respectively
+	uint32_t get_heap_size_commit_32() const;
+	void get_heap_size_commit(uint32_t& size) const;
+	uint64_t get_heap_size_commit_64() const;
+	void get_heap_size_commit(uint64_t& size) const;
+	//Returns heap size reserve for PE32 and PE64 respectively
+	uint32_t get_heap_size_reserve_32() const;
+	void get_heap_size_reserve(uint32_t& size) const;
+	uint64_t get_heap_size_reserve_64() const;
+	void get_heap_size_reserve(uint64_t& size) const;
+	//Returns stack size commit for PE32 and PE64 respectively
+	uint32_t get_stack_size_commit_32() const;
+	void get_stack_size_commit(uint32_t& size) const;
+	uint64_t get_stack_size_commit_64() const;
+	void get_stack_size_commit(uint64_t& size) const;
+	//Returns stack size reserve for PE32 and PE64 respectively
+	uint32_t get_stack_size_reserve_32() const;
+	void get_stack_size_reserve(uint32_t& size) const;
+	uint64_t get_stack_size_reserve_64() const;
+	void get_stack_size_reserve(uint64_t& size) const;
+
+	//Updates virtual size of image corresponding to section virtual sizes
+	void update_image_size();
+
+	//Returns checksum of PE file from header
+	uint32_t get_checksum() const;
+	//Sets checksum of PE file
+	void set_checksum(uint32_t checksum);
+	
+	//Returns timestamp of PE file from header
+	uint32_t get_time_date_stamp() const;
+	//Sets timestamp of PE file
+	void set_time_date_stamp(uint32_t timestamp);
+	
+	//Returns Machine field value of PE file from header
+	uint16_t get_machine() const;
+	//Sets Machine field value of PE file
+	void set_machine(uint16_t machine);
+
+	//Returns data from the beginning of image
+	//Size = SizeOfHeaders
+	const std::string& get_full_headers_data() const;
+	
+	typedef std::multimap<uint32_t, std::string> debug_data_list;
+	//Returns raw list of debug data
+	const debug_data_list& get_raw_debug_data_list() const;
+	
+	//Reads and checks DOS header
+	static void read_dos_header(std::istream& file, pe_win::image_dos_header& header);
+	
+	//Returns sizeof() nt headers
+	uint32_t get_sizeof_nt_header() const;
+	//Returns sizeof() optional headers
+	uint32_t get_sizeof_opt_headers() const;
+	//Returns raw nt headers data pointer
+	const char* get_nt_headers_ptr() const;
+	
+	//Sets size of headers (to NT headers)
+	void set_size_of_headers(uint32_t size);
+	//Sets size of optional headers (to NT headers)
+	void set_size_of_optional_header(uint16_t size);
+	
+	//Sets base of code
+	void set_base_of_code(uint32_t base);
+	//Returns base of code
+	uint32_t get_base_of_code() const;
+
+public: //ADDRESS CONVERTIONS
+	//Virtual Address (VA) to Relative Virtual Address (RVA) convertions
+	//for PE32 and PE64 respectively
+	//bound_check checks integer overflow
+	uint32_t va_to_rva(uint32_t va, bool bound_check = true) const;
+	uint32_t va_to_rva(uint64_t va, bool bound_check = true) const;
+
+	//Relative Virtual Address (RVA) to Virtual Address (VA) convertions
+	//for PE32 and PE64 respectively
+	uint32_t rva_to_va_32(uint32_t rva) const;
+	void rva_to_va(uint32_t rva, uint32_t& va) const;
+	uint64_t rva_to_va_64(uint32_t rva) const;
+	void rva_to_va(uint32_t rva, uint64_t& va) const;
+
+	//RVA to RAW file offset convertion (4gb max)
+	uint32_t rva_to_file_offset(uint32_t rva) const;
+	//RAW file offset to RVA convertion (4gb max)
+	uint32_t file_offset_to_rva(uint32_t offset) const;
+
+	//RVA from section raw data offset
+	static uint32_t rva_from_section_offset(const section& s, uint32_t raw_offset_from_section_start);
+
+public: //IMAGE SECTIONS
+	//Returns number of sections from PE header
+	uint16_t get_number_of_sections() const;
+
+	//Updates number of sections in PE header
+	uint16_t update_number_of_sections();
+
+	//Returns section alignment
+	uint32_t get_section_alignment() const;
+
+	//Returns section list
+	section_list& get_image_sections();
+	const section_list& get_image_sections() const;
+
+	//Realigns all sections, if you made any changes to sections or alignments
+	void realign_all_sections();
+	//Resligns section with specified index
+	void realign_section(uint32_t index);
+
+	//Returns section from RVA inside it
+	section& section_from_rva(uint32_t rva);
+	const section& section_from_rva(uint32_t rva) const;
+	//Returns section from directory ID
+	section& section_from_directory(uint32_t directory_id);
+	const section& section_from_directory(uint32_t directory_id) const;
+	//Returns section from VA inside it for PE32 and PE64 respectively
+	section& section_from_va(uint32_t va);
+	const section& section_from_va(uint32_t va) const;
+	section& section_from_va(uint64_t va);
+	const section& section_from_va(uint64_t va) const;
+	//Returns section from file offset (4gb max)
+	section& section_from_file_offset(uint32_t offset);
+	const section& section_from_file_offset(uint32_t offset) const;
+
+	//Returns section TOTAL RAW/VIRTUAL data length from RVA inside section
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	uint32_t section_data_length_from_rva(uint32_t rva, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	//Returns section TOTAL RAW/VIRTUAL data length from VA inside section for PE32 and PE64 respectively
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	uint32_t section_data_length_from_va(uint32_t va, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	uint32_t section_data_length_from_va(uint64_t va, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+
+	//Returns section remaining RAW/VIRTUAL data length from RVA to the end of section "s" (checks bounds)
+	uint32_t section_data_length_from_rva(const section& s, uint32_t rva_inside, section_data_type datatype = section_data_raw) const;
+	//Returns section remaining RAW/VIRTUAL data length from VA to the end of section "s" for PE32 and PE64 respectively (checks bounds)
+	uint32_t section_data_length_from_va(const section& s, uint64_t va_inside, section_data_type datatype = section_data_raw) const;
+	uint32_t section_data_length_from_va(const section& s, uint32_t va_inside, section_data_type datatype = section_data_raw) const;
+
+	//Returns section remaining RAW/VIRTUAL data length from RVA "rva_inside" to the end of section containing RVA "rva"
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	uint32_t section_data_length_from_rva(uint32_t rva, uint32_t rva_inside, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	//Returns section remaining RAW/VIRTUAL data length from VA "va_inside" to the end of section containing VA "va" for PE32 and PE64 respectively
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	uint32_t section_data_length_from_va(uint32_t va, uint32_t va_inside, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	uint32_t section_data_length_from_va(uint64_t va, uint64_t va_inside, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	//Returns corresponding section data pointer from RVA inside section
+	char* section_data_from_rva(uint32_t rva, bool include_headers = false);
+	const char* section_data_from_rva(uint32_t rva, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	//Returns corresponding section data pointer from VA inside section for PE32 and PE64 respectively
+	char* section_data_from_va(uint32_t va, bool include_headers = false);
+	const char* section_data_from_va(uint32_t va, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+	char* section_data_from_va(uint64_t va, bool include_headers = false);
+	const char* section_data_from_va(uint64_t va, section_data_type datatype = section_data_raw, bool include_headers = false) const;
+
+	//Returns corresponding section data pointer from RVA inside section "s" (checks bounds)
+	char* section_data_from_rva(section& s, uint32_t rva);
+	const char* section_data_from_rva(const section& s, uint32_t rva, section_data_type datatype = section_data_raw) const;
+	//Returns corresponding section data pointer from VA inside section "s" for PE32 and PE64 respectively (checks bounds)
+	char* section_data_from_va(section& s, uint32_t va); //Always returns raw data
+	const char* section_data_from_va(const section& s, uint32_t va, section_data_type datatype = section_data_raw) const;
+	char* section_data_from_va(section& s, uint64_t va); //Always returns raw data
+	const char* section_data_from_va(const section& s, uint64_t va, section_data_type datatype = section_data_raw) const;
+
+	//Returns corresponding section data pointer from RVA inside section "s" (checks bounds, checks sizes, the most safe function)
+	template<typename T>
+	T section_data_from_rva(const section& s, uint32_t rva, section_data_type datatype = section_data_raw) const
+	{
+		if(rva >= s.get_virtual_address() && rva < s.get_virtual_address() + s.get_aligned_virtual_size(get_section_alignment()) && pe_utils::is_sum_safe(rva, sizeof(T)))
+		{
+			const std::string& data = datatype == section_data_raw ? s.get_raw_data() : s.get_virtual_data(get_section_alignment());
+			//Don't check for underflow here, comparsion is unsigned
+			if(data.size() < rva - s.get_virtual_address() + sizeof(T))
+				throw pe_exception("RVA and requested data size does not exist inside section", pe_exception::rva_not_exists);
+
+			return *reinterpret_cast<const T*>(data.data() + rva - s.get_virtual_address());
+		}
+
+		throw pe_exception("RVA not found inside section", pe_exception::rva_not_exists);
+	}
+
+	//Returns corresponding section data pointer from RVA inside section (checks rva, checks sizes, the most safe function)
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	template<typename T>
+	T section_data_from_rva(uint32_t rva, section_data_type datatype = section_data_raw, bool include_headers = false) const
+	{
+		//if RVA is inside of headers and we're searching them too...
+		if(include_headers && pe_utils::is_sum_safe(rva, sizeof(T)) && (rva + sizeof(T) < full_headers_data_.length()))
+			return *reinterpret_cast<const T*>(&full_headers_data_[rva]);
+
+		const section& s = section_from_rva(rva);
+		const std::string& data = datatype == section_data_raw ? s.get_raw_data() : s.get_virtual_data(get_section_alignment());
+		//Don't check for underflow here, comparsion is unsigned
+		if(data.size() < rva - s.get_virtual_address() + sizeof(T))
+			throw pe_exception("RVA and requested data size does not exist inside section", pe_exception::rva_not_exists);
+
+		return *reinterpret_cast<const T*>(data.data() + rva - s.get_virtual_address());
+	}
+
+	//Returns corresponding section data pointer from VA inside section "s" (checks bounds, checks sizes, the most safe function)
+	template<typename T>
+	T section_data_from_va(const section& s, uint32_t va, section_data_type datatype = section_data_raw) const
+	{
+		return section_data_from_rva<T>(s, va_to_rva(va), datatype);
+	}
+
+	template<typename T>
+	T section_data_from_va(const section& s, uint64_t va, section_data_type datatype = section_data_raw) const
+	{
+		return section_data_from_rva<T>(s, va_to_rva(va), datatype);
+	}
+
+	//Returns corresponding section data pointer from VA inside section (checks rva, checks sizes, the most safe function)
+	//If include_headers = true, data from the beginning of PE file to SizeOfHeaders will be searched, too
+	template<typename T>
+	T section_data_from_va(uint32_t va, section_data_type datatype = section_data_raw, bool include_headers = false) const
+	{
+		return section_data_from_rva<T>(va_to_rva(va), datatype, include_headers);
+	}
+
+	template<typename T>
+	T section_data_from_va(uint64_t va, section_data_type datatype = section_data_raw, bool include_headers = false) const
+	{
+		return section_data_from_rva<T>(va_to_rva(va), datatype, include_headers);
+	}
+
+	//Returns section and offset (raw data only) from its start from RVA
+	const std::pair<uint32_t, const section*> section_and_offset_from_rva(uint32_t rva) const;
+
+	//Sets virtual size of section "s"
+	//Section must be free (not bound to any image)
+	//or the last section of this image
+	//Function calls update_image_size automatically in second case
+	void set_section_virtual_size(section& s, uint32_t vsize);
+
+	//Represents section expand type for expand_section function
+	enum section_expand_type
+	{
+		expand_section_raw, //Section raw data size will be expanded
+		expand_section_virtual //Section virtual data size will be expanded
+	};
+
+	//Expands section raw or virtual size to hold data from specified RVA with specified size
+	//Section must be free (not bound to any image)
+	//or the last section of this image
+	//Returns true if section was expanded
+	bool expand_section(section& s, uint32_t needed_rva, uint32_t needed_size, section_expand_type expand);
+
+	//Adds section to image
+	//Returns last section
+	section& add_section(section s);
+	//Prepares section to later add it to image (checks and recalculates virtual and raw section size)
+	//Section must be prepared by this function before calling add_section
+	void prepare_section(section& s);
+
+	//Returns true if sectios "s" is already attached to this PE file
+	bool section_attached(const section& s) const;
+
+
+public: //IMAGE
+	//Returns PE type (PE or PE+) from pe_type enumeration (minimal correctness checks)
+	static pe_type get_pe_type(std::istream& file);
+	//Returns PE type of this image
+	pe_type get_pe_type() const;
+
+	//Returns true if image has overlay data at the end of file
+	bool has_overlay() const;
+
+	//Realigns file (changes file alignment)
+	void realign_file(uint32_t new_file_alignment);
+	
+	//Helper function to recalculate RAW and virtual section sizes and strip it, if necessary
+	//auto_strip = strip section, if necessary
+	void recalculate_section_sizes(section& s, bool auto_strip);
+
+	// ========== END OF PUBLIC MEMBERS AND STRUCTURES ========== //
+private:
+	//Image DOS header
+	pe_win::image_dos_header dos_header_;
+	//Rich (stub) overlay data (for MSVS)
+	std::string rich_overlay_;
+	//List of image sections
+	section_list sections_;
+	//True if image has overlay
+	bool has_overlay_;
+	//Raw SizeOfHeaders-sized data from the beginning of image
+	std::string full_headers_data_;
+	//Raw debug data for all directories
+	//PointerToRawData; Data
+	debug_data_list debug_data_;
+	//PE or PE+ related properties
+	pe_properties* props_;
+
+	//Reads and checks DOS header
+	void read_dos_header(std::istream& file);
+
+	//Reads and checks PE headers and section headers, data
+	void read_pe(std::istream& file, bool read_debug_raw_data);
+
+	//Sets number of sections
+	void set_number_of_sections(uint16_t number);
+	//Sets size of image
+	void set_size_of_image(uint32_t size);
+	//Sets file alignment (no checks)
+	void set_file_alignment_unchecked(uint32_t alignment);
+	//Returns needed magic of image
+	uint32_t get_needed_magic() const;
+	//Returns nt headers data pointer
+	char* get_nt_headers_ptr();
+
+private:
+	static const uint16_t maximum_number_of_sections = 0x60;
+	static const uint32_t minimum_file_alignment = 512;
+
+private:
+	//RAW file offset to section convertion helpers (4gb max)
+	section_list::const_iterator file_offset_to_section(uint32_t offset) const;
+	section_list::iterator file_offset_to_section(uint32_t offset);
+};
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_bliss.h b/irdb-lib/pebliss/trunk/pe_lib/pe_bliss.h
new file mode 100644
index 0000000000000000000000000000000000000000..f5a8bbbb6382bc79202288e9858ea74fb372bd0d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_bliss.h
@@ -0,0 +1,21 @@
+#ifndef pebliss_pe_bliss_h
+#define pebliss_pe_bliss_h
+#pragma once
+#include "pe_base.h"
+#include "pe_rebuilder.h"
+#include "pe_factory.h"
+#include "pe_bound_import.h"
+#include "pe_debug.h"
+#include "pe_dotnet.h"
+#include "pe_exception_directory.h"
+#include "pe_exports.h"
+#include "pe_imports.h"
+#include "pe_load_config.h"
+#include "pe_relocations.h"
+#include "pe_resources.h"
+#include "pe_rich_data.h"
+#include "pe_tls.h"
+#include "pe_properties_generic.h"
+#include "pe_checksum.h"
+#include "entropy.h"
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_bliss_resources.h b/irdb-lib/pebliss/trunk/pe_lib/pe_bliss_resources.h
new file mode 100644
index 0000000000000000000000000000000000000000..cb6515f25a98575a75e8824d1971db0bdc0f80ee
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_bliss_resources.h
@@ -0,0 +1,18 @@
+#ifndef pebliss_pe_bliss_resources_h
+#define pebliss_pe_bliss_resources_h
+#pragma once
+#include "file_version_info.h"
+#include "message_table.h"
+#include "pe_resource_manager.h"
+#include "pe_resource_viewer.h"
+#include "version_info_editor.h"
+#include "version_info_viewer.h"
+#include "resource_bitmap_reader.h"
+#include "resource_bitmap_writer.h"
+#include "resource_cursor_icon_reader.h"
+#include "resource_cursor_icon_writer.h"
+#include "resource_version_info_reader.h"
+#include "resource_version_info_writer.h"
+#include "resource_string_table_reader.h"
+#include "resource_message_list_reader.h"
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_bound_import.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_bound_import.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..605cf229b42bb66b88d8c754bf09ac6e95276300
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_bound_import.cpp
@@ -0,0 +1,290 @@
+#include <string.h>
+#include "pe_bound_import.h"
+#include "utils.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//BOUND IMPORT
+//Default constructor
+bound_import_ref::bound_import_ref()
+	:timestamp_(0)
+{}
+
+//Constructor from data
+bound_import_ref::bound_import_ref(const std::string& module_name, uint32_t timestamp)
+	:module_name_(module_name), timestamp_(timestamp)
+{}
+
+//Returns imported module name
+const std::string& bound_import_ref::get_module_name() const
+{
+	return module_name_;
+}
+
+//Returns bound import date and time stamp
+uint32_t bound_import_ref::get_timestamp() const
+{
+	return timestamp_;
+}
+
+//Sets module name
+void bound_import_ref::set_module_name(const std::string& module_name)
+{
+	module_name_ = module_name;
+}
+
+//Sets timestamp
+void bound_import_ref::set_timestamp(uint32_t timestamp)
+{
+	timestamp_ = timestamp;
+}
+
+//Default constructor
+bound_import::bound_import()
+	:timestamp_(0)
+{}
+
+//Constructor from data
+bound_import::bound_import(const std::string& module_name, uint32_t timestamp)
+	:module_name_(module_name), timestamp_(timestamp)
+{}
+
+//Returns imported module name
+const std::string& bound_import::get_module_name() const
+{
+	return module_name_;
+}
+
+//Returns bound import date and time stamp
+uint32_t bound_import::get_timestamp() const
+{
+	return timestamp_;
+}
+
+//Returns bound references cound
+size_t bound_import::get_module_ref_count() const
+{
+	return refs_.size();
+}
+
+//Returns module references
+const bound_import::ref_list& bound_import::get_module_ref_list() const
+{
+	return refs_;
+}
+
+//Adds module reference
+void bound_import::add_module_ref(const bound_import_ref& ref)
+{
+	refs_.push_back(ref);
+}
+
+//Clears module references list
+void bound_import::clear_module_refs()
+{
+	refs_.clear();
+}
+
+//Returns module references
+bound_import::ref_list& bound_import::get_module_ref_list()
+{
+	return refs_;
+}
+
+//Sets module name
+void bound_import::set_module_name(const std::string& module_name)
+{
+	module_name_ = module_name;
+}
+
+//Sets timestamp
+void bound_import::set_timestamp(uint32_t timestamp)
+{
+	timestamp_ = timestamp;
+}
+
+const bound_import_module_list get_bound_import_module_list(const pe_base& pe)
+{
+	//Returned bound import modules list
+	bound_import_module_list ret;
+
+	//If image has no bound imports
+	if(!pe.has_bound_import())
+		return ret;
+
+	uint32_t bound_import_data_len =
+		pe.section_data_length_from_rva(pe.get_directory_rva(image_directory_entry_bound_import), pe.get_directory_rva(image_directory_entry_bound_import), section_data_raw, true);
+
+	if(bound_import_data_len < pe.get_directory_size(image_directory_entry_bound_import))
+		throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+	
+	const char* bound_import_data = pe.section_data_from_rva(pe.get_directory_rva(image_directory_entry_bound_import), section_data_raw, true);
+
+	//Check read in "read_pe" function raw bound import data size
+	if(bound_import_data_len < sizeof(image_bound_import_descriptor))
+		throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+	//current bound_import_data_ in-string position
+	unsigned long current_pos = 0;
+	//first bound import descriptor
+	//so, we're working with raw data here, no section helpers available
+	const image_bound_import_descriptor* descriptor = reinterpret_cast<const image_bound_import_descriptor*>(&bound_import_data[current_pos]);
+
+	//Enumerate until zero
+	while(descriptor->OffsetModuleName)
+	{
+		//Check module name offset
+		if(descriptor->OffsetModuleName >= bound_import_data_len)
+			throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+		//Check module name for null-termination
+		if(!pe_utils::is_null_terminated(&bound_import_data[descriptor->OffsetModuleName], bound_import_data_len - descriptor->OffsetModuleName))
+			throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+		//Create bound import descriptor structure
+		bound_import elem(&bound_import_data[descriptor->OffsetModuleName], descriptor->TimeDateStamp);
+
+		//Check DWORDs
+		if(descriptor->NumberOfModuleForwarderRefs >= pe_utils::max_dword / sizeof(image_bound_forwarder_ref)
+			|| !pe_utils::is_sum_safe(current_pos, 2 /* this descriptor and the next one */ * sizeof(image_bound_import_descriptor) + descriptor->NumberOfModuleForwarderRefs * sizeof(image_bound_forwarder_ref)))
+			throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+		//Move after current descriptor
+		current_pos += sizeof(image_bound_import_descriptor);
+
+		//Enumerate referenced bound import descriptors
+		for(unsigned long i = 0; i != descriptor->NumberOfModuleForwarderRefs; ++i)
+		{
+			//They're just after parent descriptor
+			//Check size of structure
+			if(current_pos + sizeof(image_bound_forwarder_ref) > bound_import_data_len)
+				throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+			//Get IMAGE_BOUND_FORWARDER_REF pointer
+			const image_bound_forwarder_ref* ref_descriptor = reinterpret_cast<const image_bound_forwarder_ref*>(&bound_import_data[current_pos]);
+
+			//Check referenced module name
+			if(ref_descriptor->OffsetModuleName >= bound_import_data_len)
+				throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+			//And its null-termination
+			if(!pe_utils::is_null_terminated(&bound_import_data[ref_descriptor->OffsetModuleName], bound_import_data_len - ref_descriptor->OffsetModuleName))
+				throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+			//Add referenced module to current bound import structure
+			elem.add_module_ref(bound_import_ref(&bound_import_data[ref_descriptor->OffsetModuleName], ref_descriptor->TimeDateStamp));
+
+			//Move after referenced bound import descriptor
+			current_pos += sizeof(image_bound_forwarder_ref);
+		}
+
+		//Check structure size
+		if(current_pos + sizeof(image_bound_import_descriptor) > bound_import_data_len)
+			throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+
+		//Move to next bound import descriptor
+		descriptor = reinterpret_cast<const image_bound_import_descriptor*>(&bound_import_data[current_pos]);
+
+		//Save created descriptor structure and references
+		ret.push_back(elem);
+	}
+
+	//Return result
+	return ret;
+}
+
+//imports - bound imported modules list
+//imports_section - section where export directory will be placed (must be attached to PE image)
+//offset_from_section_start - offset from imports_section raw data start
+//save_to_pe_headers - if true, new bound import directory information will be saved to PE image headers
+//auto_strip_last_section - if true and bound imports are placed in the last section, it will be automatically stripped
+const image_directory rebuild_bound_imports(pe_base& pe, const bound_import_module_list& imports, section& imports_section, uint32_t offset_from_section_start, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	//Check that exports_section is attached to this PE image
+	if(!pe.section_attached(imports_section))
+		throw pe_exception("Bound import section must be attached to PE file", pe_exception::section_is_not_attached);
+
+	uint32_t directory_pos = pe_utils::align_up(offset_from_section_start, sizeof(uint32_t));
+	uint32_t needed_size = sizeof(image_bound_import_descriptor) /* Ending null descriptor */;
+	uint32_t needed_size_for_strings = 0;
+
+	//Calculate needed size for bound import data
+	for(bound_import_module_list::const_iterator it = imports.begin(); it != imports.end(); ++it)
+	{
+		const bound_import& import = *it;
+		needed_size += sizeof(image_bound_import_descriptor);
+		needed_size_for_strings += static_cast<uint32_t>((*it).get_module_name().length()) + 1 /* nullbyte */;
+
+		const bound_import::ref_list& refs = import.get_module_ref_list();
+		for(bound_import::ref_list::const_iterator ref_it = refs.begin(); ref_it != refs.end(); ++ref_it)
+		{
+			needed_size_for_strings += static_cast<uint32_t>((*ref_it).get_module_name().length()) + 1 /* nullbyte */;
+			needed_size += sizeof(image_bound_forwarder_ref);
+		}
+	}
+	
+	needed_size += needed_size_for_strings;
+	
+	//Check if imports_section is last one. If it's not, check if there's enough place for bound import data
+	if(&imports_section != &*(pe.get_image_sections().end() - 1) && 
+		(imports_section.empty() || pe_utils::align_up(imports_section.get_size_of_raw_data(), pe.get_file_alignment()) < needed_size + directory_pos))
+		throw pe_exception("Insufficient space for bound import directory", pe_exception::insufficient_space);
+
+	std::string& raw_data = imports_section.get_raw_data();
+
+	//This will be done only if imports_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + directory_pos)
+		raw_data.resize(needed_size + directory_pos); //Expand section raw data
+	
+	uint32_t current_pos_for_structures = directory_pos;
+	uint32_t current_pos_for_strings = current_pos_for_structures + needed_size - needed_size_for_strings;
+
+	for(bound_import_module_list::const_iterator it = imports.begin(); it != imports.end(); ++it)
+	{
+		const bound_import& import = *it;
+		image_bound_import_descriptor descriptor;
+		descriptor.NumberOfModuleForwarderRefs = static_cast<uint16_t>(import.get_module_ref_list().size());
+		descriptor.OffsetModuleName = static_cast<uint16_t>(current_pos_for_strings - directory_pos);
+		descriptor.TimeDateStamp = import.get_timestamp();
+
+		memcpy(&raw_data[current_pos_for_structures], &descriptor, sizeof(descriptor));
+		current_pos_for_structures += sizeof(descriptor);
+		
+		size_t length = import.get_module_name().length() + 1 /* nullbyte */;
+		memcpy(&raw_data[current_pos_for_strings], import.get_module_name().c_str(), length);
+		current_pos_for_strings += static_cast<uint32_t>(length);
+
+		const bound_import::ref_list& refs = import.get_module_ref_list();
+		for(bound_import::ref_list::const_iterator ref_it = refs.begin(); ref_it != refs.end(); ++ref_it)
+		{
+			const bound_import_ref& ref = *ref_it;
+			image_bound_forwarder_ref ref_descriptor = {0};
+			ref_descriptor.OffsetModuleName = static_cast<uint16_t>(current_pos_for_strings - directory_pos);
+			ref_descriptor.TimeDateStamp = ref.get_timestamp();
+
+			memcpy(&raw_data[current_pos_for_structures], &ref_descriptor, sizeof(ref_descriptor));
+			current_pos_for_structures += sizeof(ref_descriptor);
+
+			length = ref.get_module_name().length() + 1 /* nullbyte */;
+			memcpy(&raw_data[current_pos_for_strings], ref.get_module_name().c_str(), length);
+			current_pos_for_strings += static_cast<uint32_t>(length);
+		}
+	}
+
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(imports_section, auto_strip_last_section);
+	
+	image_directory ret(pe.rva_from_section_offset(imports_section, directory_pos), needed_size);
+
+	//If auto-rewrite of PE headers is required
+	if(save_to_pe_header)
+	{
+		pe.set_directory_rva(image_directory_entry_bound_import, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_bound_import, ret.get_size());
+	}
+
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_bound_import.h b/irdb-lib/pebliss/trunk/pe_lib/pe_bound_import.h
new file mode 100644
index 0000000000000000000000000000000000000000..1bc70caa8de035dc09d614729d734c1fec6713cf
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_bound_import.h
@@ -0,0 +1,90 @@
+#ifndef pebliss_pe_bound_import_h
+#define pebliss_pe_bound_import_h
+#pragma once
+#include <vector>
+#include <string>
+#include "pe_structures.h"
+#include "pe_base.h"
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Class representing bound import reference
+class bound_import_ref
+{
+public:
+	//Default constructor
+	bound_import_ref();
+	//Constructor from data
+	bound_import_ref(const std::string& module_name, uint32_t timestamp);
+
+	//Returns imported module name
+	const std::string& get_module_name() const;
+	//Returns bound import date and time stamp
+	uint32_t get_timestamp() const;
+
+public: //Setters
+	//Sets module name
+	void set_module_name(const std::string& module_name);
+	//Sets timestamp
+	void set_timestamp(uint32_t timestamp);
+
+private:
+	std::string module_name_; //Imported module name
+	uint32_t timestamp_; //Bound import timestamp
+};
+
+//Class representing image bound import information
+class bound_import
+{
+public:
+	typedef std::vector<bound_import_ref> ref_list;
+
+public:
+	//Default constructor
+	bound_import();
+	//Constructor from data
+	bound_import(const std::string& module_name, uint32_t timestamp);
+
+	//Returns imported module name
+	const std::string& get_module_name() const;
+	//Returns bound import date and time stamp
+	uint32_t get_timestamp() const;
+
+	//Returns bound references cound
+	size_t get_module_ref_count() const;
+	//Returns module references
+	const ref_list& get_module_ref_list() const;
+
+public: //Setters
+	//Sets module name
+	void set_module_name(const std::string& module_name);
+	//Sets timestamp
+	void set_timestamp(uint32_t timestamp);
+
+	//Adds module reference
+	void add_module_ref(const bound_import_ref& ref);
+	//Clears module references list
+	void clear_module_refs();
+	//Returns module references
+	ref_list& get_module_ref_list();
+
+private:
+	std::string module_name_; //Imported module name
+	uint32_t timestamp_; //Bound import timestamp
+	ref_list refs_; //Module references list
+};
+
+typedef std::vector<bound_import> bound_import_module_list;
+
+//Returns bound import information
+const bound_import_module_list get_bound_import_module_list(const pe_base& pe);//Export directory rebuilder
+
+//imports - bound imported modules list
+//imports_section - section where export directory will be placed (must be attached to PE image)
+//offset_from_section_start - offset from imports_section raw data start
+//save_to_pe_headers - if true, new bound import directory information will be saved to PE image headers
+//auto_strip_last_section - if true and bound imports are placed in the last section, it will be automatically stripped
+const image_directory rebuild_bound_imports(pe_base& pe, const bound_import_module_list& imports, section& imports_section, uint32_t offset_from_section_start = 0, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_checksum.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_checksum.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..fe3aa81b9e0ee7bbf06df48d44cfd50c15a17043
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_checksum.cpp
@@ -0,0 +1,82 @@
+#include "pe_checksum.h"
+#include "pe_structures.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Calculate checksum of image
+uint32_t calculate_checksum(std::istream& file)
+{
+	//Save istream state
+	std::ios_base::iostate state = file.exceptions();
+	std::streamoff old_offset = file.tellg();
+
+	//Checksum value
+	unsigned long long checksum = 0;
+
+	try
+	{
+		image_dos_header header;
+
+		file.exceptions(std::ios::goodbit);
+
+		//Read DOS header
+		pe_base::read_dos_header(file, header);
+
+		//Calculate PE checksum
+		file.seekg(0);
+		unsigned long long top = 0xFFFFFFFF;
+		top++;
+
+		//"CheckSum" field position in optional PE headers - it's always 64 for PE and PE+
+		static const unsigned long checksum_pos_in_optional_headers = 64;
+		//Calculate real PE headers "CheckSum" field position
+		//Sum is safe here
+		unsigned long pe_checksum_pos = header.e_lfanew + sizeof(image_file_header) + sizeof(uint32_t) + checksum_pos_in_optional_headers;
+
+		//Calculate checksum for each byte of file
+		std::streamoff filesize = pe_utils::get_file_size(file);
+		for(unsigned long long i = 0; i < (unsigned long long) filesize; i += 4)
+		{
+			unsigned long dw = 0;
+
+			//Read DWORD from file
+			file.read(reinterpret_cast<char*>(&dw), sizeof(unsigned long));
+			//Skip "CheckSum" DWORD
+			if(i == pe_checksum_pos)
+				continue;
+
+			//Calculate checksum
+			checksum = (checksum & 0xffffffff) + dw + (checksum >> 32);
+			if(checksum > top)
+				checksum = (checksum & 0xffffffff) + (checksum >> 32);
+		}
+
+		//Finish checksum
+		checksum = (checksum & 0xffff) + (checksum >> 16);
+		checksum = (checksum) + (checksum >> 16);
+		checksum = checksum & 0xffff;
+
+		checksum += static_cast<unsigned long>(filesize);
+	}
+	catch(const std::exception&)
+	{
+		//If something went wrong, restore istream state
+		file.exceptions(state);
+		file.seekg(old_offset);
+		file.clear();
+		//Rethrow
+		throw;
+	}
+
+	//Restore istream state
+	file.exceptions(state);
+	file.seekg(old_offset);
+	file.clear();
+
+	//Return checksum
+	return static_cast<uint32_t>(checksum);	
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_checksum.h b/irdb-lib/pebliss/trunk/pe_lib/pe_checksum.h
new file mode 100644
index 0000000000000000000000000000000000000000..5be9fe94b4d726888b4474e9cd7f7174ddabcc52
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_checksum.h
@@ -0,0 +1,12 @@
+#ifndef pebliss_pe_checksum_h
+#define pebliss_pe_checksum_h
+#pragma once
+#include <istream>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+//Calculate checksum of image (performs no checks on PE structures)
+uint32_t calculate_checksum(std::istream& file);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_debug.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_debug.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..f077f29fb852e9021dec723846bb90493a41ed5c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_debug.cpp
@@ -0,0 +1,844 @@
+#include <string.h>
+#include "pe_debug.h"
+#include "utils.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+//DEBUG
+//Default constructor
+debug_info::debug_info()
+	:characteristics_(0),
+	time_stamp_(0),
+	major_version_(0), minor_version_(0),
+	type_(0),
+	size_of_data_(0),
+	address_of_raw_data_(0),
+	pointer_to_raw_data_(0),
+	advanced_info_type_(advanced_info_none)
+{}
+
+//Constructor from data
+debug_info::debug_info(const image_debug_directory& debug)
+	:characteristics_(debug.Characteristics),
+	time_stamp_(debug.TimeDateStamp),
+	major_version_(debug.MajorVersion), minor_version_(debug.MinorVersion),
+	type_(debug.Type),
+	size_of_data_(debug.SizeOfData),
+	address_of_raw_data_(debug.AddressOfRawData),
+	pointer_to_raw_data_(debug.PointerToRawData),
+	advanced_info_type_(advanced_info_none)
+{}
+
+//Returns debug characteristics
+uint32_t debug_info::get_characteristics() const
+{
+	return characteristics_;
+}
+
+//Returns debug datetimestamp
+uint32_t debug_info::get_time_stamp() const
+{
+	return time_stamp_;
+}
+
+//Returns major version
+uint32_t debug_info::get_major_version() const
+{
+	return major_version_;
+}
+
+//Returns minor version
+uint32_t debug_info::get_minor_version() const
+{
+	return minor_version_;
+}
+
+//Returns type of debug info (unchecked)
+uint32_t debug_info::get_type_raw() const
+{
+	return type_;
+}
+
+//Returns type of debug info from debug_info_type enumeration
+debug_info::debug_info_type debug_info::get_type() const
+{
+	//Determine debug type
+	switch(type_)
+	{
+	case image_debug_type_coff:
+		return debug_type_coff;
+
+	case image_debug_type_codeview:
+		return debug_type_codeview;
+
+	case image_debug_type_fpo:
+		return debug_type_fpo;
+
+	case image_debug_type_misc:
+		return debug_type_misc;
+
+	case image_debug_type_exception:
+		return debug_type_exception;
+
+	case image_debug_type_fixup:
+		return debug_type_fixup;
+
+	case image_debug_type_omap_to_src:
+		return debug_type_omap_to_src;
+
+	case image_debug_type_omap_from_src:
+		return debug_type_omap_from_src;
+
+	case image_debug_type_borland:
+		return debug_type_borland;
+
+	case image_debug_type_clsid:
+		return debug_type_clsid;
+
+	case image_debug_type_reserved10:
+		return debug_type_reserved10;
+	}
+
+	return debug_type_unknown;
+}
+
+//Returns size of debug data (internal, .pdb or other file doesn't count)
+uint32_t debug_info::get_size_of_data() const
+{
+	return size_of_data_;
+}
+
+//Returns RVA of debug info when mapped to memory or zero, if info is not mapped
+uint32_t debug_info::get_rva_of_raw_data() const
+{
+	return address_of_raw_data_;
+}
+
+//Returns raw file pointer to raw data
+uint32_t debug_info::get_pointer_to_raw_data() const
+{
+	return pointer_to_raw_data_;
+}
+
+//Copy constructor
+debug_info::debug_info(const debug_info& info)
+	:characteristics_(info.characteristics_),
+	time_stamp_(info.time_stamp_),
+	major_version_(info.major_version_), minor_version_(info.minor_version_),
+	type_(info.type_),
+	size_of_data_(info.size_of_data_),
+	address_of_raw_data_(info.address_of_raw_data_),
+	pointer_to_raw_data_(info.pointer_to_raw_data_),
+	advanced_info_type_(info.advanced_info_type_)
+{
+	copy_advanced_info(info);
+}
+
+//Copy assignment operator
+debug_info& debug_info::operator=(const debug_info& info)
+{
+	copy_advanced_info(info);
+
+	characteristics_ = info.characteristics_;
+	time_stamp_ = info.time_stamp_;
+	major_version_ = info.major_version_;
+	minor_version_ = info.minor_version_;
+	type_ = info.type_;
+	size_of_data_ = info.size_of_data_;
+	address_of_raw_data_ = info.address_of_raw_data_;
+	pointer_to_raw_data_ = info.pointer_to_raw_data_;
+	advanced_info_type_ = info.advanced_info_type_;
+
+	return *this;
+}
+
+//Default constructor
+debug_info::advanced_info::advanced_info()
+	:adv_pdb_7_0_info(0) //Zero pointer to advanced data
+{}
+
+//Returns true if advanced debug info is present
+bool debug_info::advanced_info::is_present() const
+{
+	return adv_pdb_7_0_info != 0;
+}
+
+//Helper for advanced debug information copying
+void debug_info::copy_advanced_info(const debug_info& info)
+{
+	free_present_advanced_info();
+
+	switch(info.advanced_info_type_)
+	{
+	case advanced_info_pdb_7_0:
+		advanced_debug_info_.adv_pdb_7_0_info = new pdb_7_0_info(*info.advanced_debug_info_.adv_pdb_7_0_info);
+		break;
+	case advanced_info_pdb_2_0:
+		advanced_debug_info_.adv_pdb_2_0_info = new pdb_2_0_info(*info.advanced_debug_info_.adv_pdb_2_0_info);
+		break;
+	case advanced_info_misc:
+		advanced_debug_info_.adv_misc_info = new misc_debug_info(*info.advanced_debug_info_.adv_misc_info);
+		break;
+	case advanced_info_coff:
+		advanced_debug_info_.adv_coff_info = new coff_debug_info(*info.advanced_debug_info_.adv_coff_info);
+		break;
+	default:
+		break;
+	}
+
+	advanced_info_type_ = info.advanced_info_type_;
+}
+
+//Helper for clearing any present advanced debug information
+void debug_info::free_present_advanced_info()
+{
+	switch(advanced_info_type_)
+	{
+	case advanced_info_pdb_7_0:
+		delete advanced_debug_info_.adv_pdb_7_0_info;
+		break;
+	case advanced_info_pdb_2_0:
+		delete advanced_debug_info_.adv_pdb_2_0_info;
+		break;
+	case advanced_info_misc:
+		delete advanced_debug_info_.adv_misc_info;
+		break;
+	case advanced_info_coff:
+		delete advanced_debug_info_.adv_coff_info;
+		break;
+	default:
+		break;
+	}
+
+	advanced_debug_info_.adv_pdb_7_0_info = 0;
+	advanced_info_type_ = advanced_info_none;
+}
+
+//Destructor
+debug_info::~debug_info()
+{
+	free_present_advanced_info();
+}
+
+//Sets advanced debug information
+void debug_info::set_advanced_debug_info(const pdb_7_0_info& info)
+{
+	free_present_advanced_info();
+	advanced_debug_info_.adv_pdb_7_0_info = new pdb_7_0_info(info);
+	advanced_info_type_ = advanced_info_pdb_7_0;
+}
+
+void debug_info::set_advanced_debug_info(const pdb_2_0_info& info)
+{
+	free_present_advanced_info();
+	advanced_debug_info_.adv_pdb_2_0_info = new pdb_2_0_info(info);
+	advanced_info_type_ = advanced_info_pdb_2_0;
+}
+
+void debug_info::set_advanced_debug_info(const misc_debug_info& info)
+{
+	free_present_advanced_info();
+	advanced_debug_info_.adv_misc_info = new misc_debug_info(info);
+	advanced_info_type_ = advanced_info_misc;
+}
+
+void debug_info::set_advanced_debug_info(const coff_debug_info& info)
+{
+	free_present_advanced_info();
+	advanced_debug_info_.adv_coff_info = new coff_debug_info(info);
+	advanced_info_type_ = advanced_info_coff;
+}
+
+//Returns advanced debug information type
+debug_info::advanced_info_type debug_info::get_advanced_info_type() const
+{
+	return advanced_info_type_;
+}
+
+//Returns advanced debug information or throws an exception,
+//if requested information type is not contained by structure
+template<>
+const pdb_7_0_info debug_info::get_advanced_debug_info<pdb_7_0_info>() const
+{
+	if(advanced_info_type_ != advanced_info_pdb_7_0)
+		throw pe_exception("Debug info structure does not contain PDB 7.0 data", pe_exception::advanced_debug_information_request_error);
+
+	return *advanced_debug_info_.adv_pdb_7_0_info;
+}
+
+template<>
+const pdb_2_0_info debug_info::get_advanced_debug_info<pdb_2_0_info>() const
+{
+	if(advanced_info_type_ != advanced_info_pdb_2_0)
+		throw pe_exception("Debug info structure does not contain PDB 2.0 data", pe_exception::advanced_debug_information_request_error);
+
+	return *advanced_debug_info_.adv_pdb_2_0_info;
+}
+
+template<>
+const misc_debug_info debug_info::get_advanced_debug_info<misc_debug_info>() const
+{
+	if(advanced_info_type_ != advanced_info_misc)
+		throw pe_exception("Debug info structure does not contain MISC data", pe_exception::advanced_debug_information_request_error);
+
+	return *advanced_debug_info_.adv_misc_info;
+}
+
+template<>
+const coff_debug_info debug_info::get_advanced_debug_info<coff_debug_info>() const
+{
+	if(advanced_info_type_ != advanced_info_coff)
+		throw pe_exception("Debug info structure does not contain COFF data", pe_exception::advanced_debug_information_request_error);
+
+	return *advanced_debug_info_.adv_coff_info;
+}
+
+//Sets advanced debug information type, if no advanced info structure available
+void debug_info::set_advanced_info_type(advanced_info_type type)
+{
+	free_present_advanced_info();
+	if(advanced_info_type_ >= advanced_info_codeview_4_0) //Don't set info type for those types, which have advanced info structures
+		advanced_info_type_ = type;
+}
+
+//Default constructor
+pdb_7_0_info::pdb_7_0_info()
+	:age_(0)
+{
+	memset(&guid_, 0, sizeof(guid_));
+}
+
+//Constructor from data
+pdb_7_0_info::pdb_7_0_info(const CV_INFO_PDB70* info)
+	:age_(info->Age), guid_(info->Signature),
+	pdb_file_name_(reinterpret_cast<const char*>(info->PdbFileName)) //Must be checked before for null-termination
+{}
+
+//Returns debug PDB 7.0 structure GUID
+const guid pdb_7_0_info::get_guid() const
+{
+	return guid_;
+}
+
+//Returns age of build
+uint32_t pdb_7_0_info::get_age() const
+{
+	return age_;
+}
+
+//Returns PDB file name / path
+const std::string& pdb_7_0_info::get_pdb_file_name() const
+{
+	return pdb_file_name_;
+}
+
+//Default constructor
+pdb_2_0_info::pdb_2_0_info()
+	:age_(0), signature_(0)
+{}
+
+//Constructor from data
+pdb_2_0_info::pdb_2_0_info(const CV_INFO_PDB20* info)
+	:age_(info->Age), signature_(info->Signature),
+	pdb_file_name_(reinterpret_cast<const char*>(info->PdbFileName)) //Must be checked before for null-termination
+{}
+
+//Returns debug PDB 2.0 structure signature
+uint32_t pdb_2_0_info::get_signature() const
+{
+	return signature_;
+}
+
+//Returns age of build
+uint32_t pdb_2_0_info::get_age() const
+{
+	return age_;
+}
+
+//Returns PDB file name / path
+const std::string& pdb_2_0_info::get_pdb_file_name() const
+{
+	return pdb_file_name_;
+}
+
+//Default constructor
+misc_debug_info::misc_debug_info()
+	:data_type_(0), unicode_(false)
+{}
+
+//Constructor from data
+misc_debug_info::misc_debug_info(const image_debug_misc* info)
+	:data_type_(info->DataType), unicode_(info->Unicode ? true : false)
+{
+	//IMAGE_DEBUG_MISC::Data must be checked before!
+	if(info->Unicode)
+	{
+#ifdef PE_BLISS_WINDOWS
+		debug_data_unicode_ = std::wstring(reinterpret_cast<const wchar_t*>(info->Data), (info->Length - sizeof(image_debug_misc) + 1 /* BYTE[1] in the end of structure */) / 2);
+#else
+		debug_data_unicode_ = pe_utils::from_ucs2(u16string(reinterpret_cast<const unicode16_t*>(info->Data), (info->Length - sizeof(image_debug_misc) + 1 /* BYTE[1] in the end of structure */) / 2));
+#endif
+		
+		pe_utils::strip_nullbytes(debug_data_unicode_); //Strip nullbytes in the end of string
+	}
+	else
+	{
+		debug_data_ansi_ = std::string(reinterpret_cast<const char*>(info->Data), info->Length - sizeof(image_debug_misc) + 1 /* BYTE[1] in the end of structure */);
+		pe_utils::strip_nullbytes(debug_data_ansi_); //Strip nullbytes in the end of string
+	}
+}
+
+//Returns debug data type
+uint32_t misc_debug_info::get_data_type() const
+{
+	return data_type_;
+}
+
+//Returns true if data type is exe name
+bool misc_debug_info::is_exe_name() const
+{
+	return data_type_ == image_debug_misc_exename;
+}
+
+//Returns true if debug data is UNICODE
+bool misc_debug_info::is_unicode() const
+{
+	return unicode_;
+}
+
+//Returns debug data (ANSI)
+const std::string& misc_debug_info::get_data_ansi() const
+{
+	return debug_data_ansi_;
+}
+
+//Returns debug data (UNICODE)
+const std::wstring& misc_debug_info::get_data_unicode() const
+{
+	return debug_data_unicode_;
+}
+
+//Default constructor
+coff_debug_info::coff_debug_info()
+	:number_of_symbols_(0),
+	lva_to_first_symbol_(0),
+	number_of_line_numbers_(0),
+	lva_to_first_line_number_(0),
+	rva_to_first_byte_of_code_(0),
+	rva_to_last_byte_of_code_(0),
+	rva_to_first_byte_of_data_(0),
+	rva_to_last_byte_of_data_(0)
+{}
+
+//Constructor from data
+coff_debug_info::coff_debug_info(const image_coff_symbols_header* info)
+	:number_of_symbols_(info->NumberOfSymbols),
+	lva_to_first_symbol_(info->LvaToFirstSymbol),
+	number_of_line_numbers_(info->NumberOfLinenumbers),
+	lva_to_first_line_number_(info->LvaToFirstLinenumber),
+	rva_to_first_byte_of_code_(info->RvaToFirstByteOfCode),
+	rva_to_last_byte_of_code_(info->RvaToLastByteOfCode),
+	rva_to_first_byte_of_data_(info->RvaToFirstByteOfData),
+	rva_to_last_byte_of_data_(info->RvaToLastByteOfData)
+{}
+
+//Returns number of symbols
+uint32_t coff_debug_info::get_number_of_symbols() const
+{
+	return number_of_symbols_;
+}
+
+//Returns virtual address of the first symbol
+uint32_t coff_debug_info::get_lva_to_first_symbol() const
+{
+	return lva_to_first_symbol_;
+}
+
+//Returns number of line-number entries
+uint32_t coff_debug_info::get_number_of_line_numbers() const
+{
+	return number_of_line_numbers_;
+}
+
+//Returns virtual address of the first line-number entry
+uint32_t coff_debug_info::get_lva_to_first_line_number() const
+{
+	return lva_to_first_line_number_;
+}
+
+//Returns relative virtual address of the first byte of code
+uint32_t coff_debug_info::get_rva_to_first_byte_of_code() const
+{
+	return rva_to_first_byte_of_code_;
+}
+
+//Returns relative virtual address of the last byte of code
+uint32_t coff_debug_info::get_rva_to_last_byte_of_code() const
+{
+	return rva_to_last_byte_of_code_;
+}
+
+//Returns relative virtual address of the first byte of data
+uint32_t coff_debug_info::get_rva_to_first_byte_of_data() const
+{
+	return rva_to_first_byte_of_data_;
+}
+
+//Returns relative virtual address of the last byte of data
+uint32_t coff_debug_info::get_rva_to_last_byte_of_data() const
+{
+	return rva_to_last_byte_of_data_;
+}
+
+//Returns COFF symbols list
+const coff_debug_info::coff_symbols_list& coff_debug_info::get_symbols() const
+{
+	return symbols_;
+}
+
+//Adds COFF symbol
+void coff_debug_info::add_symbol(const coff_symbol& sym)
+{
+	symbols_.push_back(sym);
+}
+
+//Default constructor
+coff_debug_info::coff_symbol::coff_symbol()
+	:storage_class_(0),
+	index_(0),
+	section_number_(0), rva_(0),
+	type_(0),
+	is_filename_(false)
+{}
+
+//Returns storage class
+uint32_t coff_debug_info::coff_symbol::get_storage_class() const
+{
+	return storage_class_;
+}
+
+//Returns symbol index
+uint32_t coff_debug_info::coff_symbol::get_index() const
+{
+	return index_;
+}
+
+//Returns section number
+uint32_t coff_debug_info::coff_symbol::get_section_number() const
+{
+	return section_number_;
+}
+
+//Returns RVA
+uint32_t coff_debug_info::coff_symbol::get_rva() const
+{
+	return rva_;
+}
+
+//Returns true if structure contains file name
+bool coff_debug_info::coff_symbol::is_file() const
+{
+	return is_filename_;
+}
+
+//Returns text data (symbol or file name)
+const std::string& coff_debug_info::coff_symbol::get_symbol() const
+{
+	return name_;
+}
+
+//Sets storage class
+void coff_debug_info::coff_symbol::set_storage_class(uint32_t storage_class)
+{
+	storage_class_ = storage_class;
+}
+
+//Sets symbol index
+void coff_debug_info::coff_symbol::set_index(uint32_t index)
+{
+	index_ = index;
+}
+
+//Sets section number
+void coff_debug_info::coff_symbol::set_section_number(uint32_t section_number)
+{
+	section_number_ = section_number;
+}
+
+//Sets RVA
+void coff_debug_info::coff_symbol::set_rva(uint32_t rva)
+{
+	rva_ = rva;
+}
+
+//Sets file name
+void coff_debug_info::coff_symbol::set_file_name(const std::string& file_name)
+{
+	name_ = file_name;
+	is_filename_ = true;
+}
+
+//Sets symbol name
+void coff_debug_info::coff_symbol::set_symbol_name(const std::string& symbol_name)
+{
+	name_ = symbol_name;
+	is_filename_ = false;
+}
+
+//Returns type
+uint16_t coff_debug_info::coff_symbol::get_type() const
+{
+	return type_;
+}
+
+//Sets type
+void coff_debug_info::coff_symbol::set_type(uint16_t type)
+{
+	type_ = type;
+}
+
+//Returns debug information list
+const debug_info_list get_debug_information(const pe_base& pe)
+{
+	debug_info_list ret;
+
+	//If there's no debug directory, return empty list
+	if(!pe.has_debug())
+		return ret;
+
+	//Check the length in bytes of the section containing debug directory
+	if(pe.section_data_length_from_rva(pe.get_directory_rva(image_directory_entry_debug), pe.get_directory_rva(image_directory_entry_debug), section_data_virtual, true)
+		< sizeof(image_debug_directory))
+		throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+	unsigned long current_pos = pe.get_directory_rva(image_directory_entry_debug);
+
+	//First IMAGE_DEBUG_DIRECTORY table
+	image_debug_directory directory = pe.section_data_from_rva<image_debug_directory>(current_pos, section_data_virtual, true);
+
+	if(!pe_utils::is_sum_safe(pe.get_directory_rva(image_directory_entry_debug), pe.get_directory_size(image_directory_entry_debug)))
+		throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+	//Iterate over all IMAGE_DEBUG_DIRECTORY directories
+	while(directory.PointerToRawData
+		&& current_pos < pe.get_directory_rva(image_directory_entry_debug) + pe.get_directory_size(image_directory_entry_debug))
+	{
+		//Create debug information structure
+		debug_info info(directory);
+
+		//Find raw debug data
+		const pe_base::debug_data_list& debug_datas = pe.get_raw_debug_data_list();
+		pe_base::debug_data_list::const_iterator it = debug_datas.find(directory.PointerToRawData);
+		if(it != debug_datas.end()) //If it exists, we'll do some detailed debug info research
+		{
+			const std::string& debug_data = (*it).second;
+			switch(directory.Type)
+			{
+			case image_debug_type_coff:
+				{
+					//Check data length
+					if(debug_data.length() < sizeof(image_coff_symbols_header))
+						throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+					//Get coff header structure pointer
+					const image_coff_symbols_header* coff = reinterpret_cast<const image_coff_symbols_header*>(debug_data.data());
+
+					//Check possible overflows
+					if(coff->NumberOfSymbols >= pe_utils::max_dword / sizeof(image_symbol)
+						|| !pe_utils::is_sum_safe(coff->NumberOfSymbols * sizeof(image_symbol), coff->LvaToFirstSymbol))
+						throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+					//Check data length again
+					if(debug_data.length() < coff->NumberOfSymbols * sizeof(image_symbol) + coff->LvaToFirstSymbol)
+						throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+					//Create COFF debug info structure
+					coff_debug_info coff_info(coff);
+
+					//Enumerate debug symbols data
+					for(uint32_t i = 0; i < coff->NumberOfSymbols; ++i)
+					{
+						//Safe sum (checked above)
+						const image_symbol* sym = reinterpret_cast<const image_symbol*>(debug_data.data() + i * sizeof(image_symbol) + coff->LvaToFirstSymbol);
+
+						coff_debug_info::coff_symbol symbol;
+						symbol.set_index(i); //Save symbol index
+						symbol.set_storage_class(sym->StorageClass); //Save storage class
+						symbol.set_type(sym->Type); //Save storage class
+
+						//Check data length again
+						if(!pe_utils::is_sum_safe(i, sym->NumberOfAuxSymbols)
+							|| (i + sym->NumberOfAuxSymbols) > coff->NumberOfSymbols
+							|| debug_data.length() < (i + 1) * sizeof(image_symbol) + coff->LvaToFirstSymbol + sym->NumberOfAuxSymbols * sizeof(image_symbol))
+							throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+						//If symbol is filename
+						if(sym->StorageClass == image_sym_class_file)
+						{
+							//Save file name, it is situated just after this IMAGE_SYMBOL structure
+							std::string file_name(reinterpret_cast<const char*>(debug_data.data() + (i + 1) * sizeof(image_symbol)), sym->NumberOfAuxSymbols * sizeof(image_symbol));
+							pe_utils::strip_nullbytes(file_name);
+							symbol.set_file_name(file_name);
+
+							//Save symbol info
+							coff_info.add_symbol(symbol);
+
+							//Move to next symbol
+							i += sym->NumberOfAuxSymbols;
+							continue;
+						}
+
+						//Dump some other symbols
+						if(((sym->StorageClass == image_sym_class_static)
+							&& (sym->NumberOfAuxSymbols == 0)
+							&& (sym->SectionNumber == 1))
+							||
+							((sym->StorageClass == image_sym_class_external)
+							&& ISFCN(sym->Type)
+							&& (sym->SectionNumber > 0))
+							)
+						{
+							//Save RVA and section number
+							symbol.set_section_number(sym->SectionNumber);
+							symbol.set_rva(sym->Value);
+
+							//If symbol has short name
+							if(sym->N.Name.Short)
+							{
+								//Copy and save symbol name
+								char name_buff[9];
+								memcpy(name_buff, sym->N.ShortName, 8);
+								name_buff[8] = '\0';
+								symbol.set_symbol_name(name_buff);
+							}
+							else
+							{
+								//Symbol has long name
+
+								//Check possible overflows
+								if(!pe_utils::is_sum_safe(coff->LvaToFirstSymbol + coff->NumberOfSymbols * sizeof(image_symbol), sym->N.Name.Long))
+									throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+								//Here we have an offset to the string table
+								uint32_t symbol_offset = coff->LvaToFirstSymbol + coff->NumberOfSymbols * sizeof(image_symbol) + sym->N.Name.Long;
+
+								//Check data length
+								if(debug_data.length() < symbol_offset)
+									throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+								//Check symbol name for null-termination
+								if(!pe_utils::is_null_terminated(debug_data.data() + symbol_offset, debug_data.length() - symbol_offset))
+									throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+								//Save symbol name
+								symbol.set_symbol_name(debug_data.data() + symbol_offset);
+							}
+
+							//Save symbol info
+							coff_info.add_symbol(symbol);
+
+							//Move to next symbol
+							i += sym->NumberOfAuxSymbols;
+							continue;
+						}
+					}
+
+					info.set_advanced_debug_info(coff_info);
+				}
+				break;
+
+			case image_debug_type_codeview:
+				{
+					//Check data length
+					if(debug_data.length() < sizeof(OMFSignature*))
+						throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+					//Get POMFSignature structure pointer from the very beginning of debug data
+					const OMFSignature* sig = reinterpret_cast<const OMFSignature*>(debug_data.data());
+					if(!memcmp(sig->Signature, "RSDS", 4))
+					{
+						//Signature is "RSDS" - PDB 7.0
+
+						//Check data length
+						if(debug_data.length() < sizeof(CV_INFO_PDB70))
+							throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+						const CV_INFO_PDB70* pdb_data = reinterpret_cast<const CV_INFO_PDB70*>(debug_data.data());
+
+						//Check PDB file name null-termination
+						if(!pe_utils::is_null_terminated(pdb_data->PdbFileName, debug_data.length() - (sizeof(CV_INFO_PDB70) - 1 /* BYTE of filename in structure */)))
+							throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+						info.set_advanced_debug_info(pdb_7_0_info(pdb_data));
+					}
+					else if(!memcmp(sig->Signature, "NB10", 4))
+					{
+						//Signature is "NB10" - PDB 2.0
+
+						//Check data length
+						if(debug_data.length() < sizeof(CV_INFO_PDB20))
+							throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+						const CV_INFO_PDB20* pdb_data = reinterpret_cast<const CV_INFO_PDB20*>(debug_data.data());
+
+						//Check PDB file name null-termination
+						if(!pe_utils::is_null_terminated(pdb_data->PdbFileName, debug_data.length() - (sizeof(CV_INFO_PDB20) - 1 /* BYTE of filename in structure */)))
+							throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+						info.set_advanced_debug_info(pdb_2_0_info(pdb_data));
+					}
+					else if(!memcmp(sig->Signature, "NB09", 4))
+					{
+						//CodeView 4.0, no structures available
+						info.set_advanced_info_type(debug_info::advanced_info_codeview_4_0);
+					}
+					else if(!memcmp(sig->Signature, "NB11", 4))
+					{
+						//CodeView 5.0, no structures available
+						info.set_advanced_info_type(debug_info::advanced_info_codeview_5_0);
+					}
+					else if(!memcmp(sig->Signature, "NB05", 4))
+					{
+						//Other CodeView, no structures available
+						info.set_advanced_info_type(debug_info::advanced_info_codeview);
+					}
+				}
+
+				break;
+
+			case image_debug_type_misc:
+				{
+					//Check data length
+					if(debug_data.length() < sizeof(image_debug_misc))
+						throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+					//Get misc structure pointer
+					const image_debug_misc* misc_data = reinterpret_cast<const image_debug_misc*>(debug_data.data());
+
+					//Check misc data length
+					if(debug_data.length() < misc_data->Length /* Total length of record */)
+						throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+					//Save advanced information
+					info.set_advanced_debug_info(misc_debug_info(misc_data));
+				}
+				break;
+			}
+		}
+
+		//Save debug information structure
+		ret.push_back(info);
+
+		//Check possible overflow
+		if(!pe_utils::is_sum_safe(current_pos, sizeof(image_debug_directory)))
+			throw pe_exception("Incorrect debug directory", pe_exception::incorrect_debug_directory);
+
+		//Go to next debug entry
+		current_pos += sizeof(image_debug_directory);
+		directory = pe.section_data_from_rva<image_debug_directory>(current_pos, section_data_virtual, true);
+	}
+
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_debug.h b/irdb-lib/pebliss/trunk/pe_lib/pe_debug.h
new file mode 100644
index 0000000000000000000000000000000000000000..2b0bf9d2a74dabd7e54fb08fce0b80ad571c52ed
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_debug.h
@@ -0,0 +1,306 @@
+#ifndef pebliss_pe_debug_h
+#define pebliss_pe_debug_h
+#pragma once
+#include <vector>
+#include "pe_structures.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+//Class representing advanced RSDS (PDB 7.0) information
+class pdb_7_0_info
+{
+public:
+	//Default constructor
+	pdb_7_0_info();
+	//Constructor from data
+	explicit pdb_7_0_info(const pe_win::CV_INFO_PDB70* info);
+
+	//Returns debug PDB 7.0 structure GUID
+	const pe_win::guid get_guid() const;
+	//Returns age of build
+	uint32_t get_age() const;
+	//Returns PDB file name / path
+	const std::string& get_pdb_file_name() const;
+
+private:
+	uint32_t age_;
+	pe_win::guid guid_;
+	std::string pdb_file_name_;
+};
+
+//Class representing advanced NB10 (PDB 2.0) information
+class pdb_2_0_info
+{
+public:
+	//Default constructor
+	pdb_2_0_info();
+	//Constructor from data
+	explicit pdb_2_0_info(const pe_win::CV_INFO_PDB20* info);
+
+	//Returns debug PDB 2.0 structure signature
+	uint32_t get_signature() const;
+	//Returns age of build
+	uint32_t get_age() const;
+	//Returns PDB file name / path
+	const std::string& get_pdb_file_name() const;
+
+private:
+	uint32_t age_;
+	uint32_t signature_;
+	std::string pdb_file_name_;
+};
+
+//Class representing advanced misc (IMAGE_DEBUG_TYPE_MISC) info
+class misc_debug_info
+{
+public:
+	//Default constructor
+	misc_debug_info();
+	//Constructor from data
+	explicit misc_debug_info(const pe_win::image_debug_misc* info);
+
+	//Returns debug data type
+	uint32_t get_data_type() const;
+	//Returns true if data type is exe name
+	bool is_exe_name() const;
+
+	//Returns true if debug data is UNICODE
+	bool is_unicode() const;
+	//Returns debug data (ANSI or UNICODE)
+	const std::string& get_data_ansi() const;
+	const std::wstring& get_data_unicode() const;
+
+private:
+	uint32_t data_type_;
+	bool unicode_;
+	std::string debug_data_ansi_;
+	std::wstring debug_data_unicode_;
+};
+
+//Class representing COFF (IMAGE_DEBUG_TYPE_COFF) debug info
+class coff_debug_info
+{
+public:
+	//Structure representing COFF symbol
+	struct coff_symbol
+	{
+	public:
+		//Default constructor
+		coff_symbol();
+
+		//Returns storage class
+		uint32_t get_storage_class() const;
+		//Returns symbol index
+		uint32_t get_index() const;
+		//Returns section number
+		uint32_t get_section_number() const;
+		//Returns RVA
+		uint32_t get_rva() const;
+		//Returns type
+		uint16_t get_type() const;
+
+		//Returns true if structure contains file name
+		bool is_file() const;
+		//Returns text data (symbol or file name)
+		const std::string& get_symbol() const;
+
+	public: //These functions do not change everything inside image, they are used by PE class
+		//Sets storage class
+		void set_storage_class(uint32_t storage_class);
+		//Sets symbol index
+		void set_index(uint32_t index);
+		//Sets section number
+		void set_section_number(uint32_t section_number);
+		//Sets RVA
+		void set_rva(uint32_t rva);
+		//Sets type
+		void set_type(uint16_t type);
+
+		//Sets file name
+		void set_file_name(const std::string& file_name);
+		//Sets symbol name
+		void set_symbol_name(const std::string& symbol_name);
+
+	private:
+		uint32_t storage_class_;
+		uint32_t index_;
+		uint32_t section_number_, rva_;
+		uint16_t type_;
+		bool is_filename_;
+		std::string name_;
+	};
+
+public:
+	typedef std::vector<coff_symbol> coff_symbols_list;
+
+public:
+	//Default constructor
+	coff_debug_info();
+	//Constructor from data
+	explicit coff_debug_info(const pe_win::image_coff_symbols_header* info);
+
+	//Returns number of symbols
+	uint32_t get_number_of_symbols() const;
+	//Returns virtual address of the first symbol
+	uint32_t get_lva_to_first_symbol() const;
+	//Returns number of line-number entries
+	uint32_t get_number_of_line_numbers() const;
+	//Returns virtual address of the first line-number entry
+	uint32_t get_lva_to_first_line_number() const;
+	//Returns relative virtual address of the first byte of code
+	uint32_t get_rva_to_first_byte_of_code() const;
+	//Returns relative virtual address of the last byte of code
+	uint32_t get_rva_to_last_byte_of_code() const;
+	//Returns relative virtual address of the first byte of data
+	uint32_t get_rva_to_first_byte_of_data() const;
+	//Returns relative virtual address of the last byte of data
+	uint32_t get_rva_to_last_byte_of_data() const;
+
+	//Returns COFF symbols list
+	const coff_symbols_list& get_symbols() const;
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//Adds COFF symbol
+	void add_symbol(const coff_symbol& sym);
+
+private:
+	uint32_t number_of_symbols_;
+	uint32_t lva_to_first_symbol_;
+	uint32_t number_of_line_numbers_;
+	uint32_t lva_to_first_line_number_;
+	uint32_t rva_to_first_byte_of_code_;
+	uint32_t rva_to_last_byte_of_code_;
+	uint32_t rva_to_first_byte_of_data_;
+	uint32_t rva_to_last_byte_of_data_;
+
+private:
+	coff_symbols_list symbols_;
+};
+
+//Class representing debug information
+class debug_info
+{
+public:
+	//Enumeration of debug information types
+	enum debug_info_type
+	{
+		debug_type_unknown,
+		debug_type_coff,
+		debug_type_codeview,
+		debug_type_fpo,
+		debug_type_misc,
+		debug_type_exception,
+		debug_type_fixup,
+		debug_type_omap_to_src,
+		debug_type_omap_from_src,
+		debug_type_borland,
+		debug_type_reserved10,
+		debug_type_clsid
+	};
+
+public:
+	//Enumeration of advanced debug information types
+	enum advanced_info_type
+	{
+		advanced_info_none, //No advanced info
+		advanced_info_pdb_7_0, //PDB 7.0
+		advanced_info_pdb_2_0, //PDB 2.0
+		advanced_info_misc, //MISC debug info
+		advanced_info_coff, //COFF debug info
+		//No advanced info structures available for types below
+		advanced_info_codeview_4_0, //CodeView 4.0
+		advanced_info_codeview_5_0, //CodeView 5.0
+		advanced_info_codeview //CodeView
+	};
+
+public:
+	//Default constructor
+	debug_info();
+	//Constructor from data
+	explicit debug_info(const pe_win::image_debug_directory& debug);
+	//Copy constructor
+	debug_info(const debug_info& info);
+	//Copy assignment operator
+	debug_info& operator=(const debug_info& info);
+	//Destructor
+	~debug_info();
+
+	//Returns debug characteristics
+	uint32_t get_characteristics() const;
+	//Returns debug datetimestamp
+	uint32_t get_time_stamp() const;
+	//Returns major version
+	uint32_t get_major_version() const;
+	//Returns minor version
+	uint32_t get_minor_version() const;
+	//Returns type of debug info (unchecked)
+	uint32_t get_type_raw() const;
+	//Returns type of debug info from debug_info_type enumeration
+	debug_info_type get_type() const;
+	//Returns size of debug data (internal, .pdb or other file doesn't count)
+	uint32_t get_size_of_data() const;
+	//Returns RVA of debug info when mapped to memory or zero, if info is not mapped
+	uint32_t get_rva_of_raw_data() const;
+	//Returns raw file pointer to raw data
+	uint32_t get_pointer_to_raw_data() const;
+
+	//Returns advanced debug information type
+	advanced_info_type get_advanced_info_type() const;
+	//Returns advanced debug information or throws an exception,
+	//if requested information type is not contained by structure
+	template<typename AdvancedInfo>
+	const AdvancedInfo get_advanced_debug_info() const;
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//Sets advanced debug information
+	void set_advanced_debug_info(const pdb_7_0_info& info);
+	void set_advanced_debug_info(const pdb_2_0_info& info);
+	void set_advanced_debug_info(const misc_debug_info& info);
+	void set_advanced_debug_info(const coff_debug_info& info);
+
+	//Sets advanced debug information type, if no advanced info structure available
+	void set_advanced_info_type(advanced_info_type type);
+
+private:
+	uint32_t characteristics_;
+	uint32_t time_stamp_;
+	uint32_t major_version_, minor_version_;
+	uint32_t type_;
+	uint32_t size_of_data_;
+	uint32_t address_of_raw_data_; //RVA when mapped or 0
+	uint32_t pointer_to_raw_data_; //RAW file offset
+
+	//Union containing advanced debug information pointer
+	union advanced_info
+	{
+	public:
+		//Default constructor
+		advanced_info();
+
+		//Returns true if advanced debug info is present
+		bool is_present() const;
+
+	public:
+		pdb_7_0_info* adv_pdb_7_0_info;
+		pdb_2_0_info* adv_pdb_2_0_info;
+		misc_debug_info* adv_misc_info;
+		coff_debug_info* adv_coff_info;
+	};
+
+	//Helper for advanced debug information copying
+	void copy_advanced_info(const debug_info& info);
+	//Helper for clearing any present advanced debug information
+	void free_present_advanced_info();
+
+	advanced_info advanced_debug_info_;
+	//Advanced information type
+	advanced_info_type advanced_info_type_;
+};
+
+typedef std::vector<debug_info> debug_info_list;
+
+//Returns debug information list
+const debug_info_list get_debug_information(const pe_base& pe);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_directory.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_directory.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..57ea2212a62989fd3503b5986834d609bd9da870
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_directory.cpp
@@ -0,0 +1,38 @@
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Default constructor
+image_directory::image_directory()
+	:rva_(0), size_(0)
+{}
+
+//Constructor from data
+image_directory::image_directory(uint32_t rva, uint32_t size)
+	:rva_(rva), size_(size)
+{}
+
+//Returns RVA
+uint32_t image_directory::get_rva() const
+{
+	return rva_;
+}
+
+//Returns size
+uint32_t image_directory::get_size() const
+{
+	return size_;
+}
+
+//Sets RVA
+void image_directory::set_rva(uint32_t rva)
+{
+	rva_ = rva;
+}
+
+//Sets size
+void image_directory::set_size(uint32_t size)
+{
+	size_ = size;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_directory.h b/irdb-lib/pebliss/trunk/pe_lib/pe_directory.h
new file mode 100644
index 0000000000000000000000000000000000000000..4ec4d68c7300babad4b54a1c5a27876b312aa1cc
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_directory.h
@@ -0,0 +1,36 @@
+#ifndef pebliss_pe_directory_h
+#define pebliss_pe_directory_h
+#pragma once
+#ifndef pedir_h
+#define pedir_h
+
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+//Class representing image directory data
+class image_directory
+{
+public:
+	//Default constructor
+	image_directory();
+	//Constructor from data
+	image_directory(uint32_t rva, uint32_t size);
+
+	//Returns RVA
+	uint32_t get_rva() const;
+	//Returns size
+	uint32_t get_size() const;
+
+	//Sets RVA
+	void set_rva(uint32_t rva);
+	//Sets size
+	void set_size(uint32_t size);
+
+private:
+	uint32_t rva_;
+	uint32_t size_;
+};
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_dotnet.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_dotnet.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..5d9e483e3ffc413596001abd955ffa0459f3c846
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_dotnet.cpp
@@ -0,0 +1,165 @@
+#include <string.h>
+#include "pe_dotnet.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//.NET
+basic_dotnet_info::basic_dotnet_info()
+{
+	memset(&header_, 0, sizeof(header_));
+}
+
+//Constructor from data
+basic_dotnet_info::basic_dotnet_info(const image_cor20_header& header)
+	:header_(header)
+{}
+
+//Returns major runtime version
+uint16_t basic_dotnet_info::get_major_runtime_version() const
+{
+	return header_.MajorRuntimeVersion;
+}
+
+//Returns minor runtime version
+uint16_t basic_dotnet_info::get_minor_runtime_version() const
+{
+	return header_.MinorRuntimeVersion;
+}
+
+//Returns RVA of metadata (symbol table and startup information)
+uint32_t basic_dotnet_info::get_rva_of_metadata() const
+{
+	return header_.MetaData.VirtualAddress;
+}
+
+//Returns size of metadata (symbol table and startup information)
+uint32_t basic_dotnet_info::get_size_of_metadata() const
+{
+	return header_.MetaData.Size;
+}
+
+//Returns flags
+uint32_t basic_dotnet_info::get_flags() const
+{
+	return header_.Flags;
+}
+
+//Returns true if entry point is native
+bool basic_dotnet_info::is_native_entry_point() const
+{
+	return (header_.Flags & comimage_flags_native_entrypoint) ? true : false;
+}
+
+//Returns true if 32 bit required
+bool basic_dotnet_info::is_32bit_required() const
+{
+	return (header_.Flags & comimage_flags_32bitrequired) ? true : false;
+}
+
+//Returns true if image is IL library
+bool basic_dotnet_info::is_il_library() const
+{
+	return (header_.Flags & comimage_flags_il_library) ? true : false;
+}
+
+//Returns true if image uses IL only
+bool basic_dotnet_info::is_il_only() const
+{
+	return (header_.Flags & comimage_flags_ilonly) ? true : false;
+}
+
+//Returns entry point RVA (if entry point is native)
+//Returns entry point managed token (if entry point is managed)
+uint32_t basic_dotnet_info::get_entry_point_rva_or_token() const
+{
+	return header_.EntryPointToken;
+}
+
+//Returns RVA of managed resources
+uint32_t basic_dotnet_info::get_rva_of_resources() const
+{
+	return header_.Resources.VirtualAddress;
+}
+
+//Returns size of managed resources
+uint32_t basic_dotnet_info::get_size_of_resources() const
+{
+	return header_.Resources.Size;
+}
+
+//Returns RVA of strong name signature
+uint32_t basic_dotnet_info::get_rva_of_strong_name_signature() const
+{
+	return header_.StrongNameSignature.VirtualAddress;
+}
+
+//Returns size of strong name signature
+uint32_t basic_dotnet_info::get_size_of_strong_name_signature() const
+{
+	return header_.StrongNameSignature.Size;
+}
+
+//Returns RVA of code manager table
+uint32_t basic_dotnet_info::get_rva_of_code_manager_table() const
+{
+	return header_.CodeManagerTable.VirtualAddress;
+}
+
+//Returns size of code manager table
+uint32_t basic_dotnet_info::get_size_of_code_manager_table() const
+{
+	return header_.CodeManagerTable.Size;
+}
+
+//Returns RVA of VTable fixups
+uint32_t basic_dotnet_info::get_rva_of_vtable_fixups() const
+{
+	return header_.VTableFixups.VirtualAddress;
+}
+
+//Returns size of VTable fixups
+uint32_t basic_dotnet_info::get_size_of_vtable_fixups() const
+{
+	return header_.VTableFixups.Size;
+}
+
+//Returns RVA of export address table jumps
+uint32_t basic_dotnet_info::get_rva_of_export_address_table_jumps() const
+{
+	return header_.ExportAddressTableJumps.VirtualAddress;
+}
+
+//Returns size of export address table jumps
+uint32_t basic_dotnet_info::get_size_of_export_address_table_jumps() const
+{
+	return header_.ExportAddressTableJumps.Size;
+}
+
+//Returns RVA of managed native header
+//(precompiled header info, usually set to zero, for internal use)
+uint32_t basic_dotnet_info::get_rva_of_managed_native_header() const
+{
+	return header_.ManagedNativeHeader.VirtualAddress;
+}
+
+//Returns size of managed native header
+//(precompiled header info, usually set to zero, for internal use)
+uint32_t basic_dotnet_info::get_size_of_managed_native_header() const
+{
+	return header_.ManagedNativeHeader.Size;
+}
+
+//Returns basic .NET information
+//If image is not native, throws an exception
+const basic_dotnet_info get_basic_dotnet_info(const pe_base& pe)
+{
+	//If there's no debug directory, return empty list
+	if(!pe.is_dotnet())
+		throw pe_exception("Image does not have managed code", pe_exception::image_does_not_have_managed_code);
+
+	//Return basic .NET information
+	return basic_dotnet_info(pe.section_data_from_rva<image_cor20_header>(pe.get_directory_rva(image_directory_entry_com_descriptor), section_data_virtual, true));
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_dotnet.h b/irdb-lib/pebliss/trunk/pe_lib/pe_dotnet.h
new file mode 100644
index 0000000000000000000000000000000000000000..615be9daff4cdb66fb7f0f9a50ef8c81961130db
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_dotnet.h
@@ -0,0 +1,79 @@
+#ifndef pebliss_pe_dotnet_h
+#define pebliss_pe_dotnet_h
+#pragma once
+#include "pe_structures.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+//Class representing basic .NET header information
+class basic_dotnet_info
+{
+public:
+	//Default constructor
+	basic_dotnet_info();
+	//Constructor from data
+	explicit basic_dotnet_info(const pe_win::image_cor20_header& header);
+
+	//Returns major runtime version
+	uint16_t get_major_runtime_version() const;
+	//Returns minor runtime version
+	uint16_t get_minor_runtime_version() const;
+
+	//Returns RVA of metadata (symbol table and startup information)
+	uint32_t get_rva_of_metadata() const;
+	//Returns size of metadata (symbol table and startup information)
+	uint32_t get_size_of_metadata() const;
+
+	//Returns flags
+	uint32_t get_flags() const;
+
+	//Returns true if entry point is native
+	bool is_native_entry_point() const;
+	//Returns true if 32 bit required
+	bool is_32bit_required() const;
+	//Returns true if image is IL library
+	bool is_il_library() const;
+	//Returns true if image uses IL only
+	bool is_il_only() const;
+
+	//Returns entry point RVA (if entry point is native)
+	//Returns entry point managed token (if entry point is managed)
+	uint32_t get_entry_point_rva_or_token() const;
+
+	//Returns RVA of managed resources
+	uint32_t get_rva_of_resources() const;
+	//Returns size of managed resources
+	uint32_t get_size_of_resources() const;
+	//Returns RVA of strong name signature
+	uint32_t get_rva_of_strong_name_signature() const;
+	//Returns size of strong name signature
+	uint32_t get_size_of_strong_name_signature() const;
+	//Returns RVA of code manager table
+	uint32_t get_rva_of_code_manager_table() const;
+	//Returns size of code manager table
+	uint32_t get_size_of_code_manager_table() const;
+	//Returns RVA of VTable fixups
+	uint32_t get_rva_of_vtable_fixups() const;
+	//Returns size of VTable fixups
+	uint32_t get_size_of_vtable_fixups() const;
+	//Returns RVA of export address table jumps
+	uint32_t get_rva_of_export_address_table_jumps() const;
+	//Returns size of export address table jumps
+	uint32_t get_size_of_export_address_table_jumps() const;
+	//Returns RVA of managed native header
+	//(precompiled header info, usually set to zero, for internal use)
+	uint32_t get_rva_of_managed_native_header() const;
+	//Returns size of managed native header
+	//(precompiled header info, usually set to zero, for internal use)
+	uint32_t get_size_of_managed_native_header() const;
+
+private:
+	pe_win::image_cor20_header header_;
+};
+
+//Returns basic .NET information
+//If image is not native, throws an exception
+const basic_dotnet_info get_basic_dotnet_info(const pe_base& pe);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_exception.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_exception.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0292f8064cb2ab76daf382c63b015202d19d2aad
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_exception.cpp
@@ -0,0 +1,20 @@
+#include "pe_exception.h"
+#include <string>
+
+namespace pe_bliss
+{
+//PE exception class constructors
+pe_exception::pe_exception(const char* text, exception_id id)
+	:std::runtime_error((std::string)text), id_(id)
+{}
+
+pe_exception::pe_exception(const std::string& text, exception_id id)
+	:std::runtime_error(text), id_(id)
+{}
+
+//Returns exception ID
+pe_exception::exception_id pe_exception::get_id() const
+{
+	return id_;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_exception.h b/irdb-lib/pebliss/trunk/pe_lib/pe_exception.h
new file mode 100644
index 0000000000000000000000000000000000000000..c06a7a0d1388d289bee6df3ea27a54cab6d705d6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_exception.h
@@ -0,0 +1,115 @@
+#ifndef pebliss_pe_exception_h
+#define pebliss_pe_exception_h
+#pragma once
+#ifndef pebliss_peexception_h
+#define pebliss_peexception_h
+#include <exception>
+#include <stdexcept>
+
+namespace pe_bliss
+{
+//PE exception class
+class pe_exception : public std::runtime_error
+{
+public:
+	//Exception IDs
+	enum exception_id
+	{
+		unknown_error,
+		bad_pe_file,
+		bad_dos_header,
+		image_nt_headers_not_found,
+		error_reading_image_nt_headers,
+		error_reading_data_directories,
+		error_reading_file,
+		pe_signature_incorrect,
+		incorrect_number_of_rva_and_sizes,
+		error_changing_section_virtual_size,
+		section_number_incorrect,
+		section_table_incorrect,
+		incorrect_section_alignment,
+		incorrect_file_alignment,
+		incorrect_size_of_image,
+		incorrect_size_of_headers,
+		image_section_headers_not_found,
+		zero_section_sizes,
+		section_incorrect_addr_or_size,
+		section_not_found,
+		image_section_data_not_found,
+		no_section_found,
+		image_section_table_incorrect,
+		directory_does_not_exist,
+		rva_not_exists,
+		error_reading_section_header,
+		error_reading_overlay,
+		incorrect_address_conversion,
+
+		incorrect_export_directory,
+		incorrect_import_directory,
+		incorrect_relocation_directory,
+		incorrect_tls_directory,
+		incorrect_config_directory,
+		incorrect_bound_import_directory,
+		incorrect_resource_directory,
+		incorrect_exception_directory,
+		incorrect_debug_directory,
+
+		resource_directory_entry_error,
+		resource_directory_entry_not_found,
+		resource_data_entry_not_found,
+		resource_incorrect_bitmap,
+		resource_incorrect_icon,
+		resource_incorrect_cursor,
+		resource_incorrect_string_table,
+		resource_string_not_found,
+		resource_incorrect_message_table,
+		resource_incorrect_version_info,
+
+		advanced_debug_information_request_error,
+		image_does_not_have_managed_code,
+
+		section_is_empty,
+		data_is_empty,
+		stream_is_bad,
+
+		section_is_not_attached,
+		insufficient_space,
+
+		cannot_rebase_relocations,
+
+		exports_list_is_empty,
+		duplicate_exported_function_ordinal,
+		duplicate_exported_function_name,
+
+		version_info_string_does_not_exist,
+
+		no_more_sections_can_be_added,
+
+		no_icon_group_found,
+		no_cursor_group_found,
+
+		encoding_convertion_error,
+
+		error_expanding_section,
+
+		cannot_rebuild_image
+	};
+
+public:
+	//Class constructors
+	explicit pe_exception(const char* text, exception_id id = unknown_error);
+	explicit pe_exception(const std::string& text, exception_id id = unknown_error);
+
+	//Returns exception ID from exception_id enumeration
+	exception_id get_id() const;
+
+	//Destructor
+	virtual ~pe_exception() throw()
+	{}
+
+private:
+	exception_id id_;
+};
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_exception_directory.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_exception_directory.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3447e5bd7a53292db4582e93f7dfc505b92e9cb5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_exception_directory.cpp
@@ -0,0 +1,156 @@
+#include "pe_exception_directory.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//EXCEPTION DIRECTORY (exists on PE+ only)
+//Default constructor
+exception_entry::exception_entry()
+	:begin_address_(0), end_address_(0), unwind_info_address_(0),
+	unwind_info_version_(0),
+	flags_(0),
+	size_of_prolog_(0),
+	count_of_codes_(0),
+	frame_register_(0),
+	frame_offset_(0)
+{}
+
+//Constructor from data
+exception_entry::exception_entry(const image_runtime_function_entry& entry, const unwind_info& unwind_info)
+	:begin_address_(entry.BeginAddress), end_address_(entry.EndAddress), unwind_info_address_(entry.UnwindInfoAddress),
+	unwind_info_version_(unwind_info.Version),
+	flags_(unwind_info.Flags),
+	size_of_prolog_(unwind_info.SizeOfProlog),
+	count_of_codes_(unwind_info.CountOfCodes),
+	frame_register_(unwind_info.FrameRegister),
+	frame_offset_(unwind_info.FrameOffset)
+{}
+
+//Returns starting address of function, affected by exception unwinding
+uint32_t exception_entry::get_begin_address() const
+{
+	return begin_address_;
+}
+
+//Returns ending address of function, affected by exception unwinding
+uint32_t exception_entry::get_end_address() const
+{
+	return end_address_;
+}
+
+//Returns unwind info address
+uint32_t exception_entry::get_unwind_info_address() const
+{
+	return unwind_info_address_;
+}
+
+//Returns UNWIND_INFO structure version
+uint8_t exception_entry::get_unwind_info_version() const
+{
+	return unwind_info_version_;
+}
+
+//Returns unwind info flags
+uint8_t exception_entry::get_flags() const
+{
+	return flags_;
+}
+
+//The function has an exception handler that should be called
+//when looking for functions that need to examine exceptions
+bool exception_entry::has_exception_handler() const
+{
+	return (flags_ & unw_flag_ehandler) ? true : false;
+}
+
+//The function has a termination handler that should be called
+//when unwinding an exception
+bool exception_entry::has_termination_handler() const
+{
+	return (flags_ & unw_flag_uhandler) ? true : false;
+}
+
+//The unwind info structure is not the primary one for the procedure
+bool exception_entry::is_chaininfo() const
+{
+	return (flags_ & unw_flag_chaininfo) ? true : false;
+}
+
+//Returns size of function prolog
+uint8_t exception_entry::get_size_of_prolog() const
+{
+	return size_of_prolog_;
+}
+
+//Returns number of unwind slots
+uint8_t exception_entry::get_number_of_unwind_slots() const
+{
+	return count_of_codes_;
+}
+
+//If the function uses frame pointer
+bool exception_entry::uses_frame_pointer() const
+{
+	return frame_register_ != 0;
+}
+
+//Number of the nonvolatile register used as the frame pointer,
+//using the same encoding for the operation info field of UNWIND_CODE nodes
+uint8_t exception_entry::get_frame_pointer_register_number() const
+{
+	return frame_register_;
+}
+
+//The scaled offset from RSP that is applied to the FP reg when it is established.
+//The actual FP reg is set to RSP + 16 * this number, allowing offsets from 0 to 240
+uint8_t exception_entry::get_scaled_rsp_offset() const
+{
+	return frame_offset_;
+}
+
+//Returns exception directory data (exists on PE+ only)
+//Unwind opcodes are not listed, because their format and list are subject to change
+const exception_entry_list get_exception_directory_data(const pe_base& pe)
+{
+	exception_entry_list ret;
+
+	//If image doesn't have exception directory, return empty list
+	if(!pe.has_exception_directory())
+		return ret;
+
+	//Check the length in bytes of the section containing exception directory
+	if(pe.section_data_length_from_rva(pe.get_directory_rva(image_directory_entry_exception), pe.get_directory_rva(image_directory_entry_exception), section_data_virtual, true)
+		< sizeof(image_runtime_function_entry))
+		throw pe_exception("Incorrect exception directory", pe_exception::incorrect_exception_directory);
+
+	unsigned long current_pos = pe.get_directory_rva(image_directory_entry_exception);
+
+	//Check if structures are DWORD-aligned
+	if(current_pos % sizeof(uint32_t))
+		throw pe_exception("Incorrect exception directory", pe_exception::incorrect_exception_directory);
+
+	//First IMAGE_RUNTIME_FUNCTION_ENTRY table
+	image_runtime_function_entry exception_table = pe.section_data_from_rva<image_runtime_function_entry>(current_pos, section_data_virtual, true);
+
+	//todo: virtual addresses BeginAddress and EndAddress are not checked to be inside image
+	while(exception_table.BeginAddress)
+	{
+		//Check addresses
+		if(exception_table.BeginAddress > exception_table.EndAddress)
+			throw pe_exception("Incorrect exception directory", pe_exception::incorrect_exception_directory);
+
+		//Get unwind information
+		unwind_info info = pe.section_data_from_rva<unwind_info>(exception_table.UnwindInfoAddress, section_data_virtual, true);
+
+		//Create exception entry and save it
+		ret.push_back(exception_entry(exception_table, info));
+
+		//Go to next exception entry
+		current_pos += sizeof(image_runtime_function_entry);
+		exception_table = pe.section_data_from_rva<image_runtime_function_entry>(current_pos, section_data_virtual, true);
+	}
+
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_exception_directory.h b/irdb-lib/pebliss/trunk/pe_lib/pe_exception_directory.h
new file mode 100644
index 0000000000000000000000000000000000000000..c38dfae0ac221ece63e159a498c2f1dffbfcae30
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_exception_directory.h
@@ -0,0 +1,70 @@
+#ifndef pebliss_pe_exception_directory_h
+#define pebliss_pe_exception_directory_h
+#pragma once
+#include <vector>
+#include "pe_structures.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+//Class representing exception directory entry
+class exception_entry
+{
+public:
+	//Default constructor
+	exception_entry();
+	//Constructor from data
+	exception_entry(const pe_win::image_runtime_function_entry& entry, const pe_win::unwind_info& unwind_info);
+
+	//Returns starting address of function, affected by exception unwinding
+	uint32_t get_begin_address() const;
+	//Returns ending address of function, affected by exception unwinding
+	uint32_t get_end_address() const;
+	//Returns unwind info address
+	uint32_t get_unwind_info_address() const;
+
+	//Returns UNWIND_INFO structure version
+	uint8_t get_unwind_info_version() const;
+
+	//Returns unwind info flags
+	uint8_t get_flags() const;
+	//The function has an exception handler that should be called
+	//when looking for functions that need to examine exceptions
+	bool has_exception_handler() const;
+	//The function has a termination handler that should be called
+	//when unwinding an exception
+	bool has_termination_handler() const;
+	//The unwind info structure is not the primary one for the procedure
+	bool is_chaininfo() const;
+
+	//Returns size of function prolog
+	uint8_t get_size_of_prolog() const;
+
+	//Returns number of unwind slots
+	uint8_t get_number_of_unwind_slots() const;
+
+	//If the function uses frame pointer
+	bool uses_frame_pointer() const;
+	//Number of the nonvolatile register used as the frame pointer,
+	//using the same encoding for the operation info field of UNWIND_CODE nodes
+	uint8_t get_frame_pointer_register_number() const;
+	//The scaled offset from RSP that is applied to the FP reg when it is established.
+	//The actual FP reg is set to RSP + 16 * this number, allowing offsets from 0 to 240
+	uint8_t get_scaled_rsp_offset() const;
+
+private:
+	uint32_t begin_address_, end_address_, unwind_info_address_;
+	uint8_t unwind_info_version_;
+	uint8_t flags_;
+	uint8_t size_of_prolog_;
+	uint8_t count_of_codes_;
+	uint8_t frame_register_, frame_offset_;
+};
+
+typedef std::vector<exception_entry> exception_entry_list;
+
+//Returns exception directory data (exists on PE+ only)
+//Unwind opcodes are not listed, because their format and list are subject to change
+const exception_entry_list get_exception_directory_data(const pe_base& pe);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_exports.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_exports.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..4a1bc1d82ff5c52ac4b9b12dda731b5895843e11
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_exports.cpp
@@ -0,0 +1,679 @@
+#include <set>
+#include <algorithm>
+#include <string.h>
+#include "pe_exports.h"
+#include "utils.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//EXPORTS
+//Default constructor
+exported_function::exported_function()
+	:ordinal_(0), rva_(0), has_name_(false), name_ordinal_(0), forward_(false)
+{}
+
+//Returns ordinal of function (actually, ordinal = hint + ordinal base)
+uint16_t exported_function::get_ordinal() const
+{
+	return ordinal_;
+}
+
+//Returns RVA of function
+uint32_t exported_function::get_rva() const
+{
+	return rva_;
+}
+
+//Returns name of function
+const std::string& exported_function::get_name() const
+{
+	return name_;
+}
+
+//Returns true if function has name and name ordinal
+bool exported_function::has_name() const
+{
+	return has_name_;
+}
+
+//Returns name ordinal of function
+uint16_t exported_function::get_name_ordinal() const
+{
+	return name_ordinal_;
+}
+
+//Returns true if function is forwarded to other library
+bool exported_function::is_forwarded() const
+{
+	return forward_;
+}
+
+//Returns the name of forwarded function
+const std::string& exported_function::get_forwarded_name() const
+{
+	return forward_name_;
+}
+
+//Sets ordinal of function
+void exported_function::set_ordinal(uint16_t ordinal)
+{
+	ordinal_ = ordinal;
+}
+
+//Sets RVA of function
+void exported_function::set_rva(uint32_t rva)
+{
+	rva_ = rva;
+}
+
+//Sets name of function (or clears it, if empty name is passed)
+void exported_function::set_name(const std::string& name)
+{
+	name_ = name;
+	has_name_ = !name.empty();
+}
+
+//Sets name ordinal
+void exported_function::set_name_ordinal(uint16_t name_ordinal)
+{
+	name_ordinal_ = name_ordinal;
+}
+
+//Sets forwarded function name (or clears it, if empty name is passed)
+void exported_function::set_forwarded_name(const std::string& name)
+{
+	forward_name_ = name;
+	forward_ = !name.empty();
+}
+
+//Default constructor
+export_info::export_info()
+	:characteristics_(0),
+	timestamp_(0),
+	major_version_(0),
+	minor_version_(0),
+	ordinal_base_(0),
+	number_of_functions_(0),
+	number_of_names_(0),
+	address_of_functions_(0),
+	address_of_names_(0),
+	address_of_name_ordinals_(0)
+{}
+
+//Returns characteristics
+uint32_t export_info::get_characteristics() const
+{
+	return characteristics_;
+}
+
+//Returns timestamp
+uint32_t export_info::get_timestamp() const
+{
+	return timestamp_;
+}
+
+//Returns major version
+uint16_t export_info::get_major_version() const
+{
+	return major_version_;
+}
+
+//Returns minor version
+uint16_t export_info::get_minor_version() const
+{
+	return minor_version_;
+}
+
+//Returns DLL name
+const std::string& export_info::get_name() const
+{
+	return name_;
+}
+
+//Returns ordinal base
+uint32_t export_info::get_ordinal_base() const
+{
+	return ordinal_base_;
+}
+
+//Returns number of functions
+uint32_t export_info::get_number_of_functions() const
+{
+	return number_of_functions_;
+}
+
+//Returns number of function names
+uint32_t export_info::get_number_of_names() const
+{
+	return number_of_names_;
+}
+
+//Returns RVA of function address table
+uint32_t export_info::get_rva_of_functions() const
+{
+	return address_of_functions_;
+}
+
+//Returns RVA of function name address table
+uint32_t export_info::get_rva_of_names() const
+{
+	return address_of_names_;
+}
+
+//Returns RVA of name ordinals table
+uint32_t export_info::get_rva_of_name_ordinals() const
+{
+	return address_of_name_ordinals_;
+}
+
+//Sets characteristics
+void export_info::set_characteristics(uint32_t characteristics)
+{
+	characteristics_ = characteristics;
+}
+
+//Sets timestamp
+void export_info::set_timestamp(uint32_t timestamp)
+{
+	timestamp_ = timestamp;
+}
+
+//Sets major version
+void export_info::set_major_version(uint16_t major_version)
+{
+	major_version_ = major_version;
+}
+
+//Sets minor version
+void export_info::set_minor_version(uint16_t minor_version)
+{
+	minor_version_ = minor_version;
+}
+
+//Sets DLL name
+void export_info::set_name(const std::string& name)
+{
+	name_ = name;
+}
+
+//Sets ordinal base
+void export_info::set_ordinal_base(uint32_t ordinal_base)
+{
+	ordinal_base_ = ordinal_base;
+}
+
+//Sets number of functions
+void export_info::set_number_of_functions(uint32_t number_of_functions)
+{
+	number_of_functions_ = number_of_functions;
+}
+
+//Sets number of function names
+void export_info::set_number_of_names(uint32_t number_of_names)
+{
+	number_of_names_ = number_of_names;
+}
+
+//Sets RVA of function address table
+void export_info::set_rva_of_functions(uint32_t rva_of_functions)
+{
+	address_of_functions_ = rva_of_functions;
+}
+
+//Sets RVA of function name address table
+void export_info::set_rva_of_names(uint32_t rva_of_names)
+{
+	address_of_names_ = rva_of_names;
+}
+
+//Sets RVA of name ordinals table
+void export_info::set_rva_of_name_ordinals(uint32_t rva_of_name_ordinals)
+{
+	address_of_name_ordinals_ = rva_of_name_ordinals;
+}
+
+const exported_functions_list get_exported_functions(const pe_base& pe, export_info* info);
+
+//Returns array of exported functions
+const exported_functions_list get_exported_functions(const pe_base& pe)
+{
+	return get_exported_functions(pe, 0);
+}
+
+//Returns array of exported functions and information about export
+const exported_functions_list get_exported_functions(const pe_base& pe, export_info& info)
+{
+	return get_exported_functions(pe, &info);
+}
+
+//Helper: sorts exported function list by ordinals
+struct ordinal_sorter
+{
+public:
+		bool operator()(const exported_function& func1, const exported_function& func2) const;
+};
+
+//Returns array of exported functions and information about export (if info != 0)
+const exported_functions_list get_exported_functions(const pe_base& pe, export_info* info)
+{
+	//Returned exported functions info array
+	std::vector<exported_function> ret;
+
+	if(pe.has_exports())
+	{
+		//Check the length in bytes of the section containing export directory
+		if(pe.section_data_length_from_rva(pe.get_directory_rva(image_directory_entry_export),
+			pe.get_directory_rva(image_directory_entry_export), section_data_virtual, true)
+			< sizeof(image_export_directory))
+			throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+		image_export_directory exports = pe.section_data_from_rva<image_export_directory>(pe.get_directory_rva(image_directory_entry_export), section_data_virtual, true);
+
+		unsigned long max_name_length;
+
+		if(info)
+		{
+			//Save some export info data
+			info->set_characteristics(exports.Characteristics);
+			info->set_major_version(exports.MajorVersion);
+			info->set_minor_version(exports.MinorVersion);
+
+			//Get byte count that we have for dll name
+			if((max_name_length = pe.section_data_length_from_rva(exports.Name, exports.Name, section_data_virtual, true)) < 2)
+				throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+			//Get dll name pointer
+			const char* dll_name = pe.section_data_from_rva(exports.Name, section_data_virtual, true);
+
+			//Check for null-termination
+			if(!pe_utils::is_null_terminated(dll_name, max_name_length))
+				throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+			//Save the rest of export information data
+			info->set_name(dll_name);
+			info->set_number_of_functions(exports.NumberOfFunctions);
+			info->set_number_of_names(exports.NumberOfNames);
+			info->set_ordinal_base(exports.Base);
+			info->set_rva_of_functions(exports.AddressOfFunctions);
+			info->set_rva_of_names(exports.AddressOfNames);
+			info->set_rva_of_name_ordinals(exports.AddressOfNameOrdinals);
+			info->set_timestamp(exports.TimeDateStamp);
+		}
+
+		if(!exports.NumberOfFunctions)
+			return ret;
+
+		//Check IMAGE_EXPORT_DIRECTORY fields
+		if(exports.NumberOfNames > exports.NumberOfFunctions)
+			throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+		//Check some export directory fields
+		if((!exports.AddressOfNameOrdinals && exports.AddressOfNames) ||
+			(exports.AddressOfNameOrdinals && !exports.AddressOfNames) ||
+			!exports.AddressOfFunctions
+			|| exports.NumberOfFunctions >= pe_utils::max_dword / sizeof(uint32_t)
+			|| exports.NumberOfNames > pe_utils::max_dword / sizeof(uint32_t)
+			|| !pe_utils::is_sum_safe(exports.AddressOfFunctions, exports.NumberOfFunctions * sizeof(uint32_t))
+			|| !pe_utils::is_sum_safe(exports.AddressOfNames, exports.NumberOfNames * sizeof(uint32_t))
+			|| !pe_utils::is_sum_safe(exports.AddressOfNameOrdinals, exports.NumberOfFunctions * sizeof(uint32_t))
+			|| !pe_utils::is_sum_safe(pe.get_directory_rva(image_directory_entry_export), pe.get_directory_size(image_directory_entry_export)))
+			throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+		//Check if it is enough bytes to hold AddressOfFunctions table
+		if(pe.section_data_length_from_rva(exports.AddressOfFunctions, exports.AddressOfFunctions, section_data_virtual, true)
+			< exports.NumberOfFunctions * sizeof(uint32_t))
+			throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+		if(exports.AddressOfNames)
+		{
+			//Check if it is enough bytes to hold name and ordinal tables
+			if(pe.section_data_length_from_rva(exports.AddressOfNameOrdinals, exports.AddressOfNameOrdinals, section_data_virtual, true)
+				< exports.NumberOfNames * sizeof(uint16_t))
+				throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+			if(pe.section_data_length_from_rva(exports.AddressOfNames, exports.AddressOfNames, section_data_virtual, true)
+				< exports.NumberOfNames * sizeof(uint32_t))
+				throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+		}
+		
+		for(uint32_t ordinal = 0; ordinal < exports.NumberOfFunctions; ordinal++)
+		{
+			//Get function address
+			//Sum and multiplication are safe (checked above)
+			uint32_t rva = pe.section_data_from_rva<uint32_t>(exports.AddressOfFunctions + ordinal * sizeof(uint32_t), section_data_virtual, true);
+
+			//If we have a skip
+			if(!rva)
+				continue;
+
+			exported_function func;
+			func.set_rva(rva);
+
+			if(!pe_utils::is_sum_safe(exports.Base, ordinal) || exports.Base + ordinal > pe_utils::max_word)
+				throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+			func.set_ordinal(static_cast<uint16_t>(ordinal + exports.Base));
+
+			//Scan for function name ordinal
+			for(uint32_t i = 0; i < exports.NumberOfNames; i++)
+			{
+				uint16_t ordinal2 = pe.section_data_from_rva<uint16_t>(exports.AddressOfNameOrdinals + i * sizeof(uint16_t), section_data_virtual, true);
+
+				//If function has name (and name ordinal)
+				if(ordinal == ordinal2)
+				{
+					//Get function name
+					//Sum and multiplication are safe (checked above)
+					uint32_t function_name_rva = pe.section_data_from_rva<uint32_t>(exports.AddressOfNames + i * sizeof(uint32_t), section_data_virtual, true);
+
+					//Get byte count that we have for function name
+					if((max_name_length = pe.section_data_length_from_rva(function_name_rva, function_name_rva, section_data_virtual, true)) < 2)
+						throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+					//Get function name pointer
+					const char* func_name = pe.section_data_from_rva(function_name_rva, section_data_virtual, true);
+
+					//Check for null-termination
+					if(!pe_utils::is_null_terminated(func_name, max_name_length))
+						throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+					//Save function info
+					func.set_name(func_name);
+					func.set_name_ordinal(ordinal2);
+
+					//If the function is just a redirect, save its name
+					if(rva >= pe.get_directory_rva(image_directory_entry_export) + sizeof(image_directory_entry_export) &&
+						rva < pe.get_directory_rva(image_directory_entry_export) + pe.get_directory_size(image_directory_entry_export))
+					{
+						if((max_name_length = pe.section_data_length_from_rva(rva, rva, section_data_virtual, true)) < 2)
+							throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+						//Get forwarded function name pointer
+						const char* forwarded_func_name = pe.section_data_from_rva(rva, section_data_virtual, true);
+
+						//Check for null-termination
+						if(!pe_utils::is_null_terminated(forwarded_func_name, max_name_length))
+							throw pe_exception("Incorrect export directory", pe_exception::incorrect_export_directory);
+
+						//Set the name of forwarded function
+						func.set_forwarded_name(forwarded_func_name);
+					}
+
+					break;
+				}
+			}
+
+			//Add function info to output array
+			ret.push_back(func);
+		}
+	}
+
+	return ret;
+}
+
+//Helper export functions
+//Returns pair: <ordinal base for supplied functions; maximum ordinal value for supplied functions>
+const std::pair<uint16_t, uint16_t> get_export_ordinal_limits(const exported_functions_list& exports)
+{
+	if(exports.empty())
+		return std::make_pair(0, 0);
+
+	uint16_t max_ordinal = 0; //Maximum ordinal number
+	uint16_t ordinal_base = pe_utils::max_word; //Minimum ordinal value
+	for(exported_functions_list::const_iterator it = exports.begin(); it != exports.end(); ++it)
+	{
+		const exported_function& func = (*it);
+
+		//Calculate maximum and minimum ordinal numbers
+		max_ordinal = std::max<uint16_t>(max_ordinal, func.get_ordinal());
+		ordinal_base = std::min<uint16_t>(ordinal_base, func.get_ordinal());
+	}
+
+	return std::make_pair(ordinal_base, max_ordinal);
+}
+
+//Checks if exported function name already exists
+bool exported_name_exists(const std::string& function_name, const exported_functions_list& exports)
+{
+	for(exported_functions_list::const_iterator it = exports.begin(); it != exports.end(); ++it)
+	{
+		if((*it).has_name() && (*it).get_name() == function_name)
+			return true;
+	}
+
+	return false;
+}
+
+//Checks if exported function name already exists
+bool exported_ordinal_exists(uint16_t ordinal, const exported_functions_list& exports)
+{
+	for(exported_functions_list::const_iterator it = exports.begin(); it != exports.end(); ++it)
+	{
+		if((*it).get_ordinal() == ordinal)
+			return true;
+	}
+
+	return false;
+}
+
+//Helper: sorts exported function list by ordinals
+bool ordinal_sorter::operator()(const exported_function& func1, const exported_function& func2) const
+{
+	return func1.get_ordinal() < func2.get_ordinal();
+}
+
+//Export directory rebuilder
+//info - export information
+//exported_functions_list - list of exported functions
+//exports_section - section where export directory will be placed (must be attached to PE image)
+//offset_from_section_start - offset from exports_section raw data start
+//save_to_pe_headers - if true, new export directory information will be saved to PE image headers
+//auto_strip_last_section - if true and exports are placed in the last section, it will be automatically stripped
+//number_of_functions and number_of_names parameters don't matter in "info" when rebuilding, they're calculated independently
+//characteristics, major_version, minor_version, timestamp and name are the only used members of "info" structure
+//Returns new export directory information
+//exported_functions_list is copied intentionally to be sorted by ordinal values later
+//Name ordinals in exported function don't matter, they will be recalculated
+const image_directory rebuild_exports(pe_base& pe, const export_info& info, exported_functions_list exports, section& exports_section, uint32_t offset_from_section_start, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	//Check that exports_section is attached to this PE image
+	if(!pe.section_attached(exports_section))
+		throw pe_exception("Exports section must be attached to PE file", pe_exception::section_is_not_attached);
+
+	//Needed space for strings
+	uint32_t needed_size_for_strings = static_cast<uint32_t>(info.get_name().length() + 1);
+	uint32_t number_of_names = 0; //Number of named functions
+	uint32_t max_ordinal = 0; //Maximum ordinal number
+	uint32_t ordinal_base = static_cast<uint32_t>(-1); //Minimum ordinal value
+	
+	if(exports.empty())
+		ordinal_base = info.get_ordinal_base();
+
+	uint32_t needed_size_for_function_names = 0; //Needed space for function name strings
+	uint32_t needed_size_for_function_forwards = 0; //Needed space for function forwards names
+	
+	//List all exported functions
+	//Calculate needed size for function list
+	{
+		//Also check that there're no duplicate names and ordinals
+		std::set<std::string> used_function_names;
+		std::set<uint16_t> used_function_ordinals;
+
+		for(exported_functions_list::const_iterator it = exports.begin(); it != exports.end(); ++it)
+		{
+			const exported_function& func = (*it);
+			//Calculate maximum and minimum ordinal numbers
+			max_ordinal = std::max<uint32_t>(max_ordinal, func.get_ordinal());
+			ordinal_base = std::min<uint32_t>(ordinal_base, func.get_ordinal());
+
+			//Check if ordinal is unique
+			if(!used_function_ordinals.insert(func.get_ordinal()).second)
+				throw pe_exception("Duplicate exported function ordinal", pe_exception::duplicate_exported_function_ordinal);
+			
+			if(func.has_name())
+			{
+				//If function is named
+				++number_of_names;
+				needed_size_for_function_names += static_cast<uint32_t>(func.get_name().length() + 1);
+				
+				//Check if it's name and name ordinal are unique
+				if(!used_function_names.insert(func.get_name()).second)
+					throw pe_exception("Duplicate exported function name", pe_exception::duplicate_exported_function_name);
+			}
+
+			//If function is forwarded to another DLL
+			if(func.is_forwarded())
+				needed_size_for_function_forwards += static_cast<uint32_t>(func.get_forwarded_name().length() + 1);
+		}
+	}
+	
+	//Sort functions by ordinal value
+	std::sort(exports.begin(), exports.end(), ordinal_sorter());
+
+	//Calculate needed space for different things...
+	needed_size_for_strings += needed_size_for_function_names;
+	needed_size_for_strings += needed_size_for_function_forwards;
+	uint32_t needed_size_for_function_name_ordinals = number_of_names * sizeof(uint16_t);
+	uint32_t needed_size_for_function_name_rvas = number_of_names * sizeof(uint32_t);
+	uint32_t needed_size_for_function_addresses = (max_ordinal - ordinal_base + 1) * sizeof(uint32_t);
+	
+	//Export directory header will be placed first
+	uint32_t directory_pos = pe_utils::align_up(offset_from_section_start, sizeof(uint32_t));
+
+	uint32_t needed_size = sizeof(image_export_directory); //Calculate needed size for export tables and strings
+	//sizeof(IMAGE_EXPORT_DIRECTORY) = export directory header
+
+	//Total needed space...
+	needed_size += needed_size_for_function_name_ordinals; //For list of names ordinals
+	needed_size += needed_size_for_function_addresses; //For function RVAs
+	needed_size += needed_size_for_strings; //For all strings
+	needed_size += needed_size_for_function_name_rvas; //For function name strings RVAs
+
+	//Check if exports_section is last one. If it's not, check if there's enough place for exports data
+	if(&exports_section != &*(pe.get_image_sections().end() - 1) && 
+		(exports_section.empty() || pe_utils::align_up(exports_section.get_size_of_raw_data(), pe.get_file_alignment()) < needed_size + directory_pos))
+		throw pe_exception("Insufficient space for export directory", pe_exception::insufficient_space);
+
+	std::string& raw_data = exports_section.get_raw_data();
+
+	//This will be done only if exports_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + directory_pos)
+		raw_data.resize(needed_size + directory_pos); //Expand section raw data
+
+	//Library name will be placed after it
+	uint32_t current_pos_of_function_names = static_cast<uint32_t>(info.get_name().length() + 1 + directory_pos + sizeof(image_export_directory));
+	//Next - function names
+	uint32_t current_pos_of_function_name_ordinals = current_pos_of_function_names + needed_size_for_function_names;
+	//Next - function name ordinals
+	uint32_t current_pos_of_function_forwards = current_pos_of_function_name_ordinals + needed_size_for_function_name_ordinals;
+	//Finally - function addresses
+	uint32_t current_pos_of_function_addresses = current_pos_of_function_forwards + needed_size_for_function_forwards;
+	//Next - function names RVAs
+	uint32_t current_pos_of_function_names_rvas = current_pos_of_function_addresses + needed_size_for_function_addresses;
+
+	{
+		//Create export directory and fill it
+		image_export_directory dir = {0};
+		dir.Characteristics = info.get_characteristics();
+		dir.MajorVersion = info.get_major_version();
+		dir.MinorVersion = info.get_minor_version();
+		dir.TimeDateStamp = info.get_timestamp();
+		dir.NumberOfFunctions = max_ordinal - ordinal_base + 1;
+		dir.NumberOfNames = number_of_names;
+		dir.Base = ordinal_base;
+		dir.AddressOfFunctions = pe.rva_from_section_offset(exports_section, current_pos_of_function_addresses);
+		dir.AddressOfNameOrdinals = pe.rva_from_section_offset(exports_section, current_pos_of_function_name_ordinals);
+		dir.AddressOfNames = pe.rva_from_section_offset(exports_section, current_pos_of_function_names_rvas);
+		dir.Name = pe.rva_from_section_offset(exports_section, directory_pos + sizeof(image_export_directory));
+
+		//Save it
+		memcpy(&raw_data[directory_pos], &dir, sizeof(dir));
+	}
+
+	//Sve library name
+	memcpy(&raw_data[directory_pos + sizeof(image_export_directory)], info.get_name().c_str(), info.get_name().length() + 1);
+
+	//A map to sort function names alphabetically
+	typedef std::map<std::string, uint16_t> funclist; //function name; function name ordinal
+	funclist funcs;
+
+	uint32_t last_ordinal = ordinal_base;
+	//Enumerate all exported functions
+	for(exported_functions_list::const_iterator it = exports.begin(); it != exports.end(); ++it)
+	{
+		const exported_function& func = (*it);
+
+		//If we're skipping some ordinals...
+		if(func.get_ordinal() > last_ordinal)
+		{
+			//Fill this function RVAs data with zeros
+			uint32_t len = sizeof(uint32_t) * (func.get_ordinal() - last_ordinal - 1);
+			if(len)
+			{
+				memset(&raw_data[current_pos_of_function_addresses], 0, len);
+				current_pos_of_function_addresses += len;
+			}
+			
+			//Save last encountered ordinal
+			last_ordinal = func.get_ordinal();
+		}
+		
+		//If function is named, save its name ordinal and name in sorted alphabetically order
+		if(func.has_name())
+			funcs.insert(std::make_pair(func.get_name(), static_cast<uint16_t>(func.get_ordinal() - ordinal_base))); //Calculate name ordinal
+
+		//If function is forwarded to another DLL
+		if(func.is_forwarded())
+		{
+			//Write its forwarded name and its RVA
+			uint32_t function_rva = pe.rva_from_section_offset(exports_section, current_pos_of_function_forwards);
+			memcpy(&raw_data[current_pos_of_function_addresses], &function_rva, sizeof(function_rva));
+			current_pos_of_function_addresses += sizeof(function_rva);
+
+			memcpy(&raw_data[current_pos_of_function_forwards], func.get_forwarded_name().c_str(), func.get_forwarded_name().length() + 1);
+			current_pos_of_function_forwards += static_cast<uint32_t>(func.get_forwarded_name().length() + 1);
+		}
+		else
+		{
+			//Write actual function RVA
+			uint32_t function_rva = func.get_rva();
+			memcpy(&raw_data[current_pos_of_function_addresses], &function_rva, sizeof(function_rva));
+			current_pos_of_function_addresses += sizeof(function_rva);
+		}
+	}
+	
+	//Enumerate sorted function names
+	for(funclist::const_iterator it = funcs.begin(); it != funcs.end(); ++it)
+	{
+		//Save function name RVA
+		uint32_t function_name_rva = pe.rva_from_section_offset(exports_section, current_pos_of_function_names);
+		memcpy(&raw_data[current_pos_of_function_names_rvas], &function_name_rva, sizeof(function_name_rva));
+		current_pos_of_function_names_rvas += sizeof(function_name_rva);
+
+		//Save function name
+		memcpy(&raw_data[current_pos_of_function_names], (*it).first.c_str(), (*it).first.length() + 1);
+		current_pos_of_function_names += static_cast<uint32_t>((*it).first.length() + 1);
+
+		//Save function name ordinal
+		uint16_t name_ordinal = (*it).second;
+		memcpy(&raw_data[current_pos_of_function_name_ordinals], &name_ordinal, sizeof(name_ordinal));
+		current_pos_of_function_name_ordinals += sizeof(name_ordinal);
+	}
+	
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(exports_section, auto_strip_last_section);
+	
+	image_directory ret(pe.rva_from_section_offset(exports_section, directory_pos), needed_size);
+
+	//If auto-rewrite of PE headers is required
+	if(save_to_pe_header)
+	{
+		pe.set_directory_rva(image_directory_entry_export, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_export, ret.get_size());
+	}
+
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_exports.h b/irdb-lib/pebliss/trunk/pe_lib/pe_exports.h
new file mode 100644
index 0000000000000000000000000000000000000000..6a90fe45111341c4a9f9863e0b4f051c94459035
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_exports.h
@@ -0,0 +1,166 @@
+#ifndef pebliss_pe_exports_h
+#define pebliss_pe_exports_h
+#pragma once
+#include <vector>
+#include <string>
+#include "pe_structures.h"
+#include "pe_base.h"
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Class representing exported function
+class exported_function
+{
+public:
+	//Default constructor
+	exported_function();
+
+	//Returns ordinal of function (actually, ordinal = hint + ordinal base)
+	uint16_t get_ordinal() const;
+
+	//Returns RVA of function
+	uint32_t get_rva() const;
+
+	//Returns true if function has name and name ordinal
+	bool has_name() const;
+	//Returns name of function
+	const std::string& get_name() const;
+	//Returns name ordinal of function
+	uint16_t get_name_ordinal() const;
+
+	//Returns true if function is forwarded to other library
+	bool is_forwarded() const;
+	//Returns the name of forwarded function
+	const std::string& get_forwarded_name() const;
+
+public: //Setters do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild export directory
+
+	//Sets ordinal of function
+	void set_ordinal(uint16_t ordinal);
+
+	//Sets RVA of function
+	void set_rva(uint32_t rva);
+
+	//Sets name of function (or clears it, if empty name is passed)
+	void set_name(const std::string& name);
+	//Sets name ordinal
+	void set_name_ordinal(uint16_t name_ordinal);
+
+	//Sets forwarded function name (or clears it, if empty name is passed)
+	void set_forwarded_name(const std::string& name);
+
+private:
+	uint16_t ordinal_; //Function ordinal
+	uint32_t rva_; //Function RVA
+	std::string name_; //Function name
+	bool has_name_; //true == function has name
+	uint16_t name_ordinal_; //Function name ordinal
+	bool forward_; //true == function is forwarded
+	std::string forward_name_; //Name of forwarded function
+};
+
+//Class representing export information
+class export_info
+{
+public:
+	//Default constructor
+	export_info();
+
+	//Returns characteristics
+	uint32_t get_characteristics() const;
+	//Returns timestamp
+	uint32_t get_timestamp() const;
+	//Returns major version
+	uint16_t get_major_version() const;
+	//Returns minor version
+	uint16_t get_minor_version() const;
+	//Returns DLL name
+	const std::string& get_name() const;
+	//Returns ordinal base
+	uint32_t get_ordinal_base() const;
+	//Returns number of functions
+	uint32_t get_number_of_functions() const;
+	//Returns number of function names
+	uint32_t get_number_of_names() const;
+	//Returns RVA of function address table
+	uint32_t get_rva_of_functions() const;
+	//Returns RVA of function name address table
+	uint32_t get_rva_of_names() const;
+	//Returns RVA of name ordinals table
+	uint32_t get_rva_of_name_ordinals() const;
+
+public: //Setters do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild export directory using rebuild_exports
+
+	//Sets characteristics
+	void set_characteristics(uint32_t characteristics);
+	//Sets timestamp
+	void set_timestamp(uint32_t timestamp);
+	//Sets major version
+	void set_major_version(uint16_t major_version);
+	//Sets minor version
+	void set_minor_version(uint16_t minor_version);
+	//Sets DLL name
+	void set_name(const std::string& name);
+	//Sets ordinal base
+	void set_ordinal_base(uint32_t ordinal_base);
+	//Sets number of functions
+	void set_number_of_functions(uint32_t number_of_functions);
+	//Sets number of function names
+	void set_number_of_names(uint32_t number_of_names);
+	//Sets RVA of function address table
+	void set_rva_of_functions(uint32_t rva_of_functions);
+	//Sets RVA of function name address table
+	void set_rva_of_names(uint32_t rva_of_names);
+	//Sets RVA of name ordinals table
+	void set_rva_of_name_ordinals(uint32_t rva_of_name_ordinals);
+
+private:
+	uint32_t characteristics_;
+	uint32_t timestamp_;
+	uint16_t major_version_;
+	uint16_t minor_version_;
+	std::string name_;
+	uint32_t ordinal_base_;
+	uint32_t number_of_functions_;
+	uint32_t number_of_names_;
+	uint32_t address_of_functions_;
+	uint32_t address_of_names_;
+	uint32_t address_of_name_ordinals_;
+};
+
+//Exported functions list typedef
+typedef std::vector<exported_function> exported_functions_list;
+
+//Returns array of exported functions
+const exported_functions_list get_exported_functions(const pe_base& pe);
+//Returns array of exported functions and information about export
+const exported_functions_list get_exported_functions(const pe_base& pe, export_info& info);
+	
+//Helper export functions
+//Returns pair: <ordinal base for supplied functions; maximum ordinal value for supplied functions>
+const std::pair<uint16_t, uint16_t> get_export_ordinal_limits(const exported_functions_list& exports);
+
+//Checks if exported function name already exists
+bool exported_name_exists(const std::string& function_name, const exported_functions_list& exports);
+
+//Checks if exported function ordinal already exists
+bool exported_ordinal_exists(uint16_t ordinal, const exported_functions_list& exports);
+
+//Export directory rebuilder
+//info - export information
+//exported_functions_list - list of exported functions
+//exports_section - section where export directory will be placed (must be attached to PE image)
+//offset_from_section_start - offset from exports_section raw data start
+//save_to_pe_headers - if true, new export directory information will be saved to PE image headers
+//auto_strip_last_section - if true and exports are placed in the last section, it will be automatically stripped
+//number_of_functions and number_of_names parameters don't matter in "info" when rebuilding, they're calculated independently
+//characteristics, major_version, minor_version, timestamp and name are the only used members of "info" structure
+//Returns new export directory information
+//exported_functions_list is copied intentionally to be sorted by ordinal values later
+//Name ordinals in exported function don't matter, they will be recalculated
+const image_directory rebuild_exports(pe_base& pe, const export_info& info, exported_functions_list exports, section& exports_section, uint32_t offset_from_section_start = 0, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_factory.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_factory.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..193e7e21d6bc61bc68a17e7da6a10279e964531c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_factory.cpp
@@ -0,0 +1,12 @@
+#include "pe_factory.h"
+#include "pe_properties_generic.h"
+
+namespace pe_bliss
+{
+pe_base pe_factory::create_pe(std::istream& file, bool read_debug_raw_data)
+{
+	return pe_base::get_pe_type(file) == pe_type_32
+		? pe_base(file, pe_properties_32(), read_debug_raw_data)
+		: pe_base(file, pe_properties_64(), read_debug_raw_data);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_factory.h b/irdb-lib/pebliss/trunk/pe_lib/pe_factory.h
new file mode 100644
index 0000000000000000000000000000000000000000..5ba1f13be8a63786ea8e32f67a5803d9ba8a11ea
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_factory.h
@@ -0,0 +1,19 @@
+#ifndef pebliss_pe_factory_h
+#define pebliss_pe_factory_h
+#pragma once
+#include <memory>
+#include <istream>
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+class pe_factory
+{
+public:
+	//Creates pe_base class instance from PE or PE+ istream
+	//If read_bound_import_raw_data, raw bound import data will be read (used to get bound import info)
+	//If read_debug_raw_data, raw debug data will be read (used to get image debug info)
+	static pe_base create_pe(std::istream& file, bool read_debug_raw_data = true);
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_imports.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_imports.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..704d5fca9971ebafc02d13158cf4fe0fafb2475f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_imports.cpp
@@ -0,0 +1,756 @@
+#include <string.h>
+#include "pe_imports.h"
+#include "pe_properties_generic.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//IMPORTS
+//Default constructor
+//If set_to_pe_headers = true, IMAGE_DIRECTORY_ENTRY_IMPORT entry will be reset
+//to new value after import rebuilding
+//If auto_zero_directory_entry_iat = true, IMAGE_DIRECTORY_ENTRY_IAT will be set to zero
+//IMAGE_DIRECTORY_ENTRY_IAT is used by loader to temporarily make section, where IMAGE_DIRECTORY_ENTRY_IAT RVA points, writeable
+//to be able to modify IAT thunks
+import_rebuilder_settings::import_rebuilder_settings(bool set_to_pe_headers, bool auto_zero_directory_entry_iat)
+	:offset_from_section_start_(0),
+	build_original_iat_(true),
+	save_iat_and_original_iat_rvas_(true),
+	fill_missing_original_iats_(false),
+	set_to_pe_headers_(set_to_pe_headers),
+	zero_directory_entry_iat_(auto_zero_directory_entry_iat),
+	rewrite_iat_and_original_iat_contents_(false),
+	auto_strip_last_section_(true)
+{}
+
+//Returns offset from section start where import directory data will be placed
+uint32_t import_rebuilder_settings::get_offset_from_section_start() const
+{
+	return offset_from_section_start_;
+}
+
+//Returns true if Original import address table (IAT) will be rebuilt
+bool import_rebuilder_settings::build_original_iat() const
+{
+	return build_original_iat_;
+}
+
+//Returns true if Original import address and import address tables will not be rebuilt,
+//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+bool import_rebuilder_settings::save_iat_and_original_iat_rvas() const
+{
+	return save_iat_and_original_iat_rvas_;
+}
+
+//Returns true if Original import address and import address tables contents will be rewritten
+//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+//and save_iat_and_original_iat_rvas is true
+bool import_rebuilder_settings::rewrite_iat_and_original_iat_contents() const
+{
+	return rewrite_iat_and_original_iat_contents_;
+}
+
+//Returns true if original missing IATs will be rebuilt
+//(only if IATs are saved)
+bool import_rebuilder_settings::fill_missing_original_iats() const
+{
+	return fill_missing_original_iats_;
+}
+
+//Returns true if PE headers should be updated automatically after rebuilding of imports
+bool import_rebuilder_settings::auto_set_to_pe_headers() const
+{
+	return set_to_pe_headers_;
+}
+
+//Returns true if IMAGE_DIRECTORY_ENTRY_IAT must be zeroed, works only if auto_set_to_pe_headers = true
+bool import_rebuilder_settings::zero_directory_entry_iat() const
+{
+	return zero_directory_entry_iat_;	
+}
+
+//Returns true if the last section should be stripped automatically, if imports are inside it
+bool import_rebuilder_settings::auto_strip_last_section_enabled() const
+{
+	return auto_strip_last_section_;
+}
+
+//Sets offset from section start where import directory data will be placed
+void import_rebuilder_settings::set_offset_from_section_start(uint32_t offset)
+{
+	offset_from_section_start_ = offset;
+}
+
+//Sets if Original import address table (IAT) will be rebuilt
+void import_rebuilder_settings::build_original_iat(bool enable)
+{
+	build_original_iat_ = enable;
+}
+
+//Sets if Original import address and import address tables will not be rebuilt,
+//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+void import_rebuilder_settings::save_iat_and_original_iat_rvas(bool enable, bool enable_rewrite_iat_and_original_iat_contents)
+{
+	save_iat_and_original_iat_rvas_ = enable;
+	if(save_iat_and_original_iat_rvas_)
+		rewrite_iat_and_original_iat_contents_ = enable_rewrite_iat_and_original_iat_contents;
+	else
+		rewrite_iat_and_original_iat_contents_ = false;
+}
+
+//Sets if original missing IATs will be rebuilt
+//(only if IATs are saved)
+void import_rebuilder_settings::fill_missing_original_iats(bool enable)
+{
+	fill_missing_original_iats_ = enable;
+}
+
+//Sets if PE headers should be updated automatically after rebuilding of imports
+void import_rebuilder_settings::auto_set_to_pe_headers(bool enable)
+{
+	set_to_pe_headers_ = enable;
+}
+
+//Sets if IMAGE_DIRECTORY_ENTRY_IAT must be zeroed, works only if auto_set_to_pe_headers = true
+void import_rebuilder_settings::zero_directory_entry_iat(bool enable)
+{
+	zero_directory_entry_iat_ = enable;
+}
+
+//Sets if the last section should be stripped automatically, if imports are inside it, default true
+void import_rebuilder_settings::enable_auto_strip_last_section(bool enable)
+{
+	auto_strip_last_section_ = enable;
+}
+
+//Default constructor
+imported_function::imported_function()
+	:hint_(0), ordinal_(0), iat_va_(0)
+{}
+
+//Returns name of function
+const std::string& imported_function::get_name() const
+{
+	return name_;
+}
+
+//Returns true if imported function has name (and hint)
+bool imported_function::has_name() const
+{
+	return !name_.empty();
+}
+
+//Returns hint
+uint16_t imported_function::get_hint() const
+{
+	return hint_;
+}
+
+//Returns ordinal of function
+uint16_t imported_function::get_ordinal() const
+{
+	return ordinal_;
+}
+
+//Returns IAT entry VA (usable if image has both IAT and original IAT and is bound)
+uint64_t imported_function::get_iat_va() const
+{
+	return iat_va_;
+}
+
+//Sets name of function
+void imported_function::set_name(const std::string& name)
+{
+	name_ = name;
+}
+
+//Sets hint
+void imported_function::set_hint(uint16_t hint)
+{
+	hint_ = hint;
+}
+
+//Sets ordinal
+void imported_function::set_ordinal(uint16_t ordinal)
+{
+	ordinal_ = ordinal;
+}
+
+//Sets IAT entry VA (usable if image has both IAT and original IAT and is bound)
+void imported_function::set_iat_va(uint64_t va)
+{
+	iat_va_ = va;
+}
+
+//Default constructor
+import_library::import_library()
+	:rva_to_iat_(0), rva_to_original_iat_(0), timestamp_(0)
+{}
+
+//Returns name of library
+const std::string& import_library::get_name() const
+{
+	return name_;
+}
+
+//Returns RVA to Import Address Table (IAT)
+uint32_t import_library::get_rva_to_iat() const
+{
+	return rva_to_iat_;
+}
+
+//Returns RVA to Original Import Address Table (Original IAT)
+uint32_t import_library::get_rva_to_original_iat() const
+{
+	return rva_to_original_iat_;
+}
+
+//Returns timestamp
+uint32_t import_library::get_timestamp() const
+{
+	return timestamp_;
+}
+
+//Sets name of library
+void import_library::set_name(const std::string& name)
+{
+	name_ = name;
+}
+
+//Sets RVA to Import Address Table (IAT)
+void import_library::set_rva_to_iat(uint32_t rva_to_iat)
+{
+	rva_to_iat_ = rva_to_iat;
+}
+
+//Sets RVA to Original Import Address Table (Original IAT)
+void import_library::set_rva_to_original_iat(uint32_t rva_to_original_iat)
+{
+	rva_to_original_iat_ = rva_to_original_iat;
+}
+
+//Sets timestamp
+void import_library::set_timestamp(uint32_t timestamp)
+{
+	timestamp_ = timestamp;
+}
+
+//Returns imported functions list
+const import_library::imported_list& import_library::get_imported_functions() const
+{
+	return imports_;
+}
+
+//Adds imported function
+void import_library::add_import(const imported_function& func)
+{
+	imports_.push_back(func);
+}
+
+//Clears imported functions list
+void import_library::clear_imports()
+{
+	imports_.clear();
+}
+
+const imported_functions_list get_imported_functions(const pe_base& pe)
+{
+	return (pe.get_pe_type() == pe_type_32 ?
+		get_imported_functions_base<pe_types_class_32>(pe)
+		: get_imported_functions_base<pe_types_class_64>(pe));
+}
+
+const image_directory rebuild_imports(pe_base& pe, const imported_functions_list& imports, section& import_section, const import_rebuilder_settings& import_settings)
+{
+	return (pe.get_pe_type() == pe_type_32 ?
+		rebuild_imports_base<pe_types_class_32>(pe, imports, import_section, import_settings)
+		: rebuild_imports_base<pe_types_class_64>(pe, imports, import_section, import_settings));
+}
+
+//Returns imported functions list with related libraries info
+template<typename PEClassType>
+const imported_functions_list get_imported_functions_base(const pe_base& pe)
+{
+	imported_functions_list ret;
+
+	//If image has no imports, return empty array
+	if(!pe.has_imports())
+		return ret;
+
+	unsigned long current_descriptor_pos = pe.get_directory_rva(image_directory_entry_import);
+	//Get first IMAGE_IMPORT_DESCRIPTOR
+	image_import_descriptor import_descriptor = pe.section_data_from_rva<image_import_descriptor>(current_descriptor_pos, section_data_virtual, true);
+
+	//Iterate them until we reach zero-element
+	//We don't need to check correctness of this, because exception will be thrown
+	//inside of loop if we go outsize of section
+	while(import_descriptor.Name)
+	{
+		//Get imported library information
+		import_library lib;
+
+		unsigned long max_name_length;
+		//Get byte count that we have for library name
+		if((max_name_length = pe.section_data_length_from_rva(import_descriptor.Name, import_descriptor.Name, section_data_virtual, true)) < 2)
+			throw pe_exception("Incorrect import directory", pe_exception::incorrect_import_directory);
+
+		//Get DLL name pointer
+		const char* dll_name = pe.section_data_from_rva(import_descriptor.Name, section_data_virtual, true);
+
+		//Check for null-termination
+		if(!pe_utils::is_null_terminated(dll_name, max_name_length))
+			throw pe_exception("Incorrect import directory", pe_exception::incorrect_import_directory);
+
+		//Set library name
+		lib.set_name(dll_name);
+		//Set library timestamp
+		lib.set_timestamp(import_descriptor.TimeDateStamp);
+		//Set library RVA to IAT and original IAT
+		lib.set_rva_to_iat(import_descriptor.FirstThunk);
+		lib.set_rva_to_original_iat(import_descriptor.OriginalFirstThunk);
+
+		//Get RVA to IAT (it must be filled by loader when loading PE)
+		uint32_t current_thunk_rva = import_descriptor.FirstThunk;
+		typename PEClassType::BaseSize import_address_table = pe.section_data_from_rva<typename PEClassType::BaseSize>(current_thunk_rva, section_data_virtual, true);
+
+		//Get RVA to original IAT (lookup table), which must handle imported functions names
+		//Some linkers leave this pointer zero-filled
+		//Such image is valid, but it is not possible to restore imported functions names
+		//afted image was loaded, because IAT becomes the only one table
+		//containing both function names and function RVAs after loading
+		uint32_t current_original_thunk_rva = import_descriptor.OriginalFirstThunk;
+		typename PEClassType::BaseSize import_lookup_table = current_original_thunk_rva == 0 ? import_address_table : pe.section_data_from_rva<typename PEClassType::BaseSize>(current_original_thunk_rva, section_data_virtual, true);
+		if(current_original_thunk_rva == 0)
+			current_original_thunk_rva = current_thunk_rva;
+
+		//List all imported functions for current DLL
+		if(import_lookup_table != 0 && import_address_table != 0)
+		{
+			while(true)
+			{
+				//Imported function description
+				imported_function func;
+
+				//Get VA from IAT
+				typename PEClassType::BaseSize address = pe.section_data_from_rva<typename PEClassType::BaseSize>(current_thunk_rva, section_data_virtual, true);
+				//Move pointer
+				current_thunk_rva += sizeof(typename PEClassType::BaseSize);
+
+				//Jump to next DLL if we finished with this one
+				if(!address)
+					break;
+
+				func.set_iat_va(address);
+
+				//Get VA from original IAT
+				typename PEClassType::BaseSize lookup = pe.section_data_from_rva<typename PEClassType::BaseSize>(current_original_thunk_rva, section_data_virtual, true);
+				//Move pointer
+				current_original_thunk_rva += sizeof(typename PEClassType::BaseSize);
+
+				//Check if function is imported by ordinal
+				if((lookup & PEClassType::ImportSnapFlag) != 0)
+				{
+					//Set function ordinal
+					func.set_ordinal(static_cast<uint16_t>(lookup & 0xffff));
+				}
+				else
+				{
+					//Get byte count that we have for function name
+					if(lookup > static_cast<uint32_t>(-1) - sizeof(uint16_t))
+						throw pe_exception("Incorrect import directory", pe_exception::incorrect_import_directory);
+
+					//Get maximum available length of function name
+					if((max_name_length = pe.section_data_length_from_rva(static_cast<uint32_t>(lookup + sizeof(uint16_t)), static_cast<uint32_t>(lookup + sizeof(uint16_t)), section_data_virtual, true)) < 2)
+						throw pe_exception("Incorrect import directory", pe_exception::incorrect_import_directory);
+
+					//Get imported function name
+					const char* func_name = pe.section_data_from_rva(static_cast<uint32_t>(lookup + sizeof(uint16_t)), section_data_virtual, true);
+
+					//Check for null-termination
+					if(!pe_utils::is_null_terminated(func_name, max_name_length))
+						throw pe_exception("Incorrect import directory", pe_exception::incorrect_import_directory);
+
+					//HINT in import table is ORDINAL in export table
+					uint16_t hint = pe.section_data_from_rva<uint16_t>(static_cast<uint32_t>(lookup), section_data_virtual, true);
+
+					//Save hint and name
+					func.set_name(func_name);
+					func.set_hint(hint);
+				}
+
+				//Add function to list
+				lib.add_import(func);
+			}
+		}
+
+		//Check possible overflow
+		if(!pe_utils::is_sum_safe(current_descriptor_pos, sizeof(image_import_descriptor)))
+			throw pe_exception("Incorrect import directory", pe_exception::incorrect_import_directory);
+
+		//Go to next library
+		current_descriptor_pos += sizeof(image_import_descriptor);
+		import_descriptor = pe.section_data_from_rva<image_import_descriptor>(current_descriptor_pos, section_data_virtual, true);
+
+		//Save import information
+		ret.push_back(lib);
+	}
+
+	//Return resulting list
+	return ret;
+}
+
+
+//Simple import directory rebuilder
+//You can get all image imports with get_imported_functions() function
+//You can use returned value to, for example, add new imported library with some functions
+//to the end of list of imported libraries
+//To keep PE file working, rebuild its imports with save_iat_and_original_iat_rvas = true (default)
+//Don't add new imported functions to existing imported library entries, because this can cause
+//rewriting of some used memory (or other IAT/orig.IAT fields) by system loader
+//The safest way is just adding import libraries with functions to the end of imported_functions_list array
+template<typename PEClassType>
+const image_directory rebuild_imports_base(pe_base& pe, const imported_functions_list& imports, section& import_section, const import_rebuilder_settings& import_settings)
+{
+	//Check that import_section is attached to this PE image
+	if(!pe.section_attached(import_section))
+		throw pe_exception("Import section must be attached to PE file", pe_exception::section_is_not_attached);
+
+	uint32_t needed_size = 0; //Calculate needed size for import structures and strings
+	uint32_t needed_size_for_strings = 0; //Calculate needed size for import strings (library and function names and hints)
+	uint32_t size_of_iat = 0; //Size of IAT structures
+
+	needed_size += static_cast<uint32_t>((1 /* ending null descriptor */ + imports.size()) * sizeof(image_import_descriptor));
+	
+	//Enumerate imported functions
+	for(imported_functions_list::const_iterator it = imports.begin(); it != imports.end(); ++it)
+	{
+		needed_size_for_strings += static_cast<uint32_t>((*it).get_name().length() + 1 /* nullbyte */);
+
+		const import_library::imported_list& funcs = (*it).get_imported_functions();
+
+		//IMAGE_THUNK_DATA
+		size_of_iat += static_cast<uint32_t>(sizeof(typename PEClassType::BaseSize) * (1 /*ending null */ + funcs.size()));
+
+		//Enumerate all imported functions in library
+		for(import_library::imported_list::const_iterator f = funcs.begin(); f != funcs.end(); ++f)
+		{
+			if((*f).has_name())
+				needed_size_for_strings += static_cast<uint32_t>((*f).get_name().length() + 1 /* nullbyte */ + sizeof(uint16_t) /* hint */);
+		}
+	}
+
+	if(import_settings.build_original_iat() || import_settings.fill_missing_original_iats())
+		needed_size += size_of_iat * 2; //We'll have two similar-sized IATs if we're building original IAT
+	else
+		needed_size += size_of_iat;
+
+	needed_size += sizeof(typename PEClassType::BaseSize); //Maximum align for IAT and original IAT
+	
+	//Total needed size for import structures and strings
+	needed_size += needed_size_for_strings;
+
+	//Check if import_section is last one. If it's not, check if there's enough place for import data
+	if(&import_section != &*(pe.get_image_sections().end() - 1) && 
+		(import_section.empty() || pe_utils::align_up(import_section.get_size_of_raw_data(), pe.get_file_alignment()) < needed_size + import_settings.get_offset_from_section_start()))
+		throw pe_exception("Insufficient space for import directory", pe_exception::insufficient_space);
+
+	std::string& raw_data = import_section.get_raw_data();
+
+	//This will be done only if image_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + import_settings.get_offset_from_section_start())
+		raw_data.resize(needed_size + import_settings.get_offset_from_section_start()); //Expand section raw data
+	
+	uint32_t current_string_pointer = import_settings.get_offset_from_section_start();/* we will paste structures after strings */
+	
+	//Position for IAT
+	uint32_t current_pos_for_iat = pe_utils::align_up(static_cast<uint32_t>(needed_size_for_strings + import_settings.get_offset_from_section_start() + (1 + imports.size()) * sizeof(image_import_descriptor)), sizeof(typename PEClassType::BaseSize));
+	//Position for original IAT
+	uint32_t current_pos_for_original_iat = current_pos_for_iat + size_of_iat;
+	//Position for import descriptors
+	uint32_t current_pos_for_descriptors = needed_size_for_strings + import_settings.get_offset_from_section_start();
+
+	//Build imports
+	for(imported_functions_list::const_iterator it = imports.begin(); it != imports.end(); ++it)
+	{
+		//Create import descriptor
+		image_import_descriptor descr;
+		memset(&descr, 0, sizeof(descr));
+		descr.TimeDateStamp = (*it).get_timestamp(); //Restore timestamp
+		descr.Name = pe.rva_from_section_offset(import_section, current_string_pointer); //Library name RVA
+
+		//If we should save IAT for current import descriptor
+		bool save_iats_for_this_descriptor = import_settings.save_iat_and_original_iat_rvas() && (*it).get_rva_to_iat() != 0;
+		//If we should write original IAT
+		bool write_original_iat = (!save_iats_for_this_descriptor && import_settings.build_original_iat()) || import_settings.fill_missing_original_iats();
+
+		//If we should rewrite saved original IAT for current import descriptor (without changing its position)
+		bool rewrite_saved_original_iat = save_iats_for_this_descriptor && import_settings.rewrite_iat_and_original_iat_contents() && import_settings.build_original_iat();
+		//If we should rewrite saved IAT for current import descriptor (without changing its position)
+		bool rewrite_saved_iat = save_iats_for_this_descriptor && import_settings.rewrite_iat_and_original_iat_contents() && (*it).get_rva_to_iat() != 0;
+
+		//Helper values if we're rewriting existing IAT or orig.IAT
+		uint32_t original_first_thunk = 0;
+		uint32_t first_thunk = 0;
+
+		if(save_iats_for_this_descriptor)
+		{
+			//If there's no original IAT and we're asked to rebuild missing original IATs
+			if(!(*it).get_rva_to_original_iat() && import_settings.fill_missing_original_iats())
+				descr.OriginalFirstThunk = import_settings.build_original_iat() ? pe.rva_from_section_offset(import_section, current_pos_for_original_iat) : 0;
+			else
+				descr.OriginalFirstThunk = import_settings.build_original_iat() ? (*it).get_rva_to_original_iat() : 0;
+			
+			descr.FirstThunk = (*it).get_rva_to_iat();
+
+			original_first_thunk = descr.OriginalFirstThunk;
+			first_thunk = descr.FirstThunk;
+
+			if(rewrite_saved_original_iat)
+			{
+				if((*it).get_rva_to_original_iat())
+					write_original_iat = true;
+				else
+					rewrite_saved_original_iat = false;
+			}
+
+			if(rewrite_saved_iat)
+				save_iats_for_this_descriptor = false;
+		}
+		else
+		{
+			//We are creating new IAT and original IAT (if needed)
+			descr.OriginalFirstThunk = import_settings.build_original_iat() ? pe.rva_from_section_offset(import_section, current_pos_for_original_iat) : 0;
+			descr.FirstThunk = pe.rva_from_section_offset(import_section, current_pos_for_iat);
+		}
+		
+		//Save import descriptor
+		memcpy(&raw_data[current_pos_for_descriptors], &descr, sizeof(descr));
+		current_pos_for_descriptors += sizeof(descr);
+
+		//Save library name
+		memcpy(&raw_data[current_string_pointer], (*it).get_name().c_str(), (*it).get_name().length() + 1 /* nullbyte */);
+		current_string_pointer += static_cast<uint32_t>((*it).get_name().length() + 1 /* nullbyte */);
+		
+		//List all imported functions
+		const import_library::imported_list& funcs = (*it).get_imported_functions();
+		for(import_library::imported_list::const_iterator f = funcs.begin(); f != funcs.end(); ++f)
+		{
+			if((*f).has_name()) //If function is imported by name
+			{
+				//Get RVA of IMAGE_IMPORT_BY_NAME
+				typename PEClassType::BaseSize rva_of_named_import = pe.rva_from_section_offset(import_section, current_string_pointer);
+
+				if(!save_iats_for_this_descriptor)
+				{
+					if(write_original_iat)
+					{
+						//We're creating original IATs - so we can write to IAT saved VA (because IMAGE_IMPORT_BY_NAME will be read
+						//by PE loader from original IAT)
+						typename PEClassType::BaseSize iat_value = static_cast<typename PEClassType::BaseSize>((*f).get_iat_va());
+
+						if(rewrite_saved_iat)
+						{
+							if(pe.section_data_length_from_rva(first_thunk, first_thunk, section_data_raw, true) <= sizeof(iat_value))
+								throw pe_exception("Insufficient space inside initial IAT", pe_exception::insufficient_space);
+
+							memcpy(pe.section_data_from_rva(first_thunk, true), &iat_value, sizeof(iat_value));
+
+							first_thunk += sizeof(iat_value);
+						}
+						else
+						{
+							memcpy(&raw_data[current_pos_for_iat], &iat_value, sizeof(iat_value));
+							current_pos_for_iat += sizeof(rva_of_named_import);
+						}
+					}
+					else
+					{
+						//Else - write to IAT RVA of IMAGE_IMPORT_BY_NAME
+						if(rewrite_saved_iat)
+						{
+							if(pe.section_data_length_from_rva(first_thunk, first_thunk, section_data_raw, true) <= sizeof(rva_of_named_import))
+								throw pe_exception("Insufficient space inside initial IAT", pe_exception::insufficient_space);
+
+							memcpy(pe.section_data_from_rva(first_thunk, true), &rva_of_named_import, sizeof(rva_of_named_import));
+
+							first_thunk += sizeof(rva_of_named_import);
+						}
+						else
+						{
+							memcpy(&raw_data[current_pos_for_iat], &rva_of_named_import, sizeof(rva_of_named_import));
+							current_pos_for_iat += sizeof(rva_of_named_import);
+						}
+					}
+				}
+
+				if(write_original_iat)
+				{
+					if(rewrite_saved_original_iat)
+					{
+						if(pe.section_data_length_from_rva(original_first_thunk, original_first_thunk, section_data_raw, true) <= sizeof(rva_of_named_import))
+							throw pe_exception("Insufficient space inside initial original IAT", pe_exception::insufficient_space);
+
+						memcpy(pe.section_data_from_rva(original_first_thunk, true), &rva_of_named_import, sizeof(rva_of_named_import));
+
+						original_first_thunk += sizeof(rva_of_named_import);
+					}
+					else
+					{
+						//We're creating original IATs
+						memcpy(&raw_data[current_pos_for_original_iat], &rva_of_named_import, sizeof(rva_of_named_import));
+						current_pos_for_original_iat += sizeof(rva_of_named_import);
+					}
+				}
+
+				//Write IMAGE_IMPORT_BY_NAME (WORD hint + string function name)
+				uint16_t hint = (*f).get_hint();
+				memcpy(&raw_data[current_string_pointer], &hint, sizeof(hint));
+				memcpy(&raw_data[current_string_pointer + sizeof(uint16_t)], (*f).get_name().c_str(), (*f).get_name().length() + 1 /* nullbyte */);
+				current_string_pointer += static_cast<uint32_t>((*f).get_name().length() + 1 /* nullbyte */ + sizeof(uint16_t) /* hint */);
+			}
+			else //Function is imported by ordinal
+			{
+				uint16_t ordinal = (*f).get_ordinal();
+				typename PEClassType::BaseSize thunk_value = ordinal;
+				thunk_value |= PEClassType::ImportSnapFlag; //Imported by ordinal
+
+				if(!save_iats_for_this_descriptor)
+				{
+					if(write_original_iat)
+					{
+						//We're creating original IATs - so we can wtire to IAT saved VA (because ordinal will be read
+						//by PE loader from original IAT)
+						typename PEClassType::BaseSize iat_value = static_cast<typename PEClassType::BaseSize>((*f).get_iat_va());
+						if(rewrite_saved_iat)
+						{
+							if(pe.section_data_length_from_rva(first_thunk, first_thunk, section_data_raw, true) <= sizeof(iat_value))
+								throw pe_exception("Insufficient space inside initial IAT", pe_exception::insufficient_space);
+
+							memcpy(pe.section_data_from_rva(first_thunk, true), &iat_value, sizeof(iat_value));
+
+							first_thunk += sizeof(iat_value);
+						}
+						else
+						{
+							memcpy(&raw_data[current_pos_for_iat], &iat_value, sizeof(iat_value));
+							current_pos_for_iat += sizeof(thunk_value);
+						}
+					}
+					else
+					{
+						//Else - write ordinal to IAT
+						if(rewrite_saved_iat)
+						{
+							if(pe.section_data_length_from_rva(first_thunk, first_thunk, section_data_raw, true) <= sizeof(thunk_value))
+								throw pe_exception("Insufficient space inside initial IAT", pe_exception::insufficient_space);
+
+							memcpy(pe.section_data_from_rva(first_thunk, true), &thunk_value, sizeof(thunk_value));
+
+							first_thunk += sizeof(thunk_value);
+						}
+						else
+						{
+							memcpy(&raw_data[current_pos_for_iat], &thunk_value, sizeof(thunk_value));
+						}
+					}
+				}
+
+				//We're writing ordinal to original IAT slot
+				if(write_original_iat)
+				{
+					if(rewrite_saved_original_iat)
+					{
+						if(pe.section_data_length_from_rva(original_first_thunk, original_first_thunk, section_data_raw, true) <= sizeof(thunk_value))
+							throw pe_exception("Insufficient space inside initial original IAT", pe_exception::insufficient_space);
+
+						memcpy(pe.section_data_from_rva(original_first_thunk, true), &thunk_value, sizeof(thunk_value));
+
+						original_first_thunk += sizeof(thunk_value);
+					}
+					else
+					{
+						memcpy(&raw_data[current_pos_for_original_iat], &thunk_value, sizeof(thunk_value));
+						current_pos_for_original_iat += sizeof(thunk_value);
+					}
+				}
+			}
+		}
+
+		if(!save_iats_for_this_descriptor)
+		{
+			//Ending null thunks
+			typename PEClassType::BaseSize thunk_value = 0;
+
+			if(rewrite_saved_iat)
+			{
+				if(pe.section_data_length_from_rva(first_thunk, first_thunk, section_data_raw, true) <= sizeof(thunk_value))
+					throw pe_exception("Insufficient space inside initial IAT", pe_exception::insufficient_space);
+
+				memcpy(pe.section_data_from_rva(first_thunk, true), &thunk_value, sizeof(thunk_value));
+
+				first_thunk += sizeof(thunk_value);
+			}
+			else
+			{
+				memcpy(&raw_data[current_pos_for_iat], &thunk_value, sizeof(thunk_value));
+				current_pos_for_iat += sizeof(thunk_value);
+			}
+		}
+
+		if(write_original_iat)
+		{
+			//Ending null thunks
+			typename PEClassType::BaseSize thunk_value = 0;
+
+			if(rewrite_saved_original_iat)
+			{
+				if(pe.section_data_length_from_rva(original_first_thunk, original_first_thunk, section_data_raw, true) <= sizeof(thunk_value))
+					throw pe_exception("Insufficient space inside initial original IAT", pe_exception::insufficient_space);
+
+				memcpy(pe.section_data_from_rva(original_first_thunk, true), &thunk_value, sizeof(thunk_value));
+
+				original_first_thunk += sizeof(thunk_value);
+			}
+			else
+			{
+				memcpy(&raw_data[current_pos_for_original_iat], &thunk_value, sizeof(thunk_value));
+				current_pos_for_original_iat += sizeof(thunk_value);
+			}
+		}
+	}
+
+	{
+		//Null ending descriptor
+		image_import_descriptor descr;
+		memset(&descr, 0, sizeof(descr));
+		memcpy(&raw_data[current_pos_for_descriptors], &descr, sizeof(descr));
+	}
+
+	//Strip data a little, if we saved some place
+	//We're allocating more space than needed, if present original IAT and IAT are saved
+	raw_data.resize(current_pos_for_original_iat);
+
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(import_section, import_settings.auto_strip_last_section_enabled());
+
+	//Return information about rebuilt import directory
+	image_directory ret(pe.rva_from_section_offset(import_section, import_settings.get_offset_from_section_start() + needed_size_for_strings), needed_size - needed_size_for_strings);
+
+	//If auto-rewrite of PE headers is required
+	if(import_settings.auto_set_to_pe_headers())
+	{
+		pe.set_directory_rva(image_directory_entry_import, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_import, ret.get_size());
+
+		//If we are requested to zero IMAGE_DIRECTORY_ENTRY_IAT also
+		if(import_settings.zero_directory_entry_iat())
+		{
+			pe.set_directory_rva(image_directory_entry_iat, 0);
+			pe.set_directory_size(image_directory_entry_iat, 0);
+		}
+	}
+
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_imports.h b/irdb-lib/pebliss/trunk/pe_lib/pe_imports.h
new file mode 100644
index 0000000000000000000000000000000000000000..b2ec9487dd4b35744a6e72a5b7db1636dc531419
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_imports.h
@@ -0,0 +1,190 @@
+#ifndef pebliss_pe_imports_h
+#define pebliss_pe_imports_h
+#pragma once
+#include <vector>
+#include <string>
+#include "pe_structures.h"
+#include "pe_directory.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+//Class representing imported function
+class imported_function
+{
+public:
+	//Default constructor
+	imported_function();
+
+	//Returns true if imported function has name (and hint)
+	bool has_name() const;
+	//Returns name of function
+	const std::string& get_name() const;
+	//Returns hint
+	uint16_t get_hint() const;
+	//Returns ordinal of function
+	uint16_t get_ordinal() const;
+
+	//Returns IAT entry VA (usable if image has both IAT and original IAT and is bound)
+	uint64_t get_iat_va() const;
+
+public: //Setters do not change everything inside image, they are used by PE class
+	//You also can use them to rebuild image imports
+	//Sets name of function
+	void set_name(const std::string& name);
+	//Sets hint
+	void set_hint(uint16_t hint);
+	//Sets ordinal
+	void set_ordinal(uint16_t ordinal);
+
+	//Sets IAT entry VA (usable if image has both IAT and original IAT and is bound)
+	void set_iat_va(uint64_t rva);
+
+private:
+	std::string name_; //Function name
+	uint16_t hint_; //Hint
+	uint16_t ordinal_; //Ordinal
+	uint64_t iat_va_;
+};
+
+//Class representing imported library information
+class import_library
+{
+public:
+	typedef std::vector<imported_function> imported_list;
+
+public:
+	//Default constructor
+	import_library();
+
+	//Returns name of library
+	const std::string& get_name() const;
+	//Returns RVA to Import Address Table (IAT)
+	uint32_t get_rva_to_iat() const;
+	//Returns RVA to Original Import Address Table (Original IAT)
+	uint32_t get_rva_to_original_iat() const;
+	//Returns timestamp
+	uint32_t get_timestamp() const;
+
+	//Returns imported functions list
+	const imported_list& get_imported_functions() const;
+
+public: //Setters do not change everything inside image, they are used by PE class
+	//You also can use them to rebuild image imports
+	//Sets name of library
+	void set_name(const std::string& name);
+	//Sets RVA to Import Address Table (IAT)
+	void set_rva_to_iat(uint32_t rva_to_iat);
+	//Sets RVA to Original Import Address Table (Original IAT)
+	void set_rva_to_original_iat(uint32_t rva_to_original_iat);
+	//Sets timestamp
+	void set_timestamp(uint32_t timestamp);
+
+	//Adds imported function
+	void add_import(const imported_function& func);
+	//Clears imported functions list
+	void clear_imports();
+
+private:
+	std::string name_; //Library name
+	uint32_t rva_to_iat_; //RVA to IAT
+	uint32_t rva_to_original_iat_; //RVA to original IAT
+	uint32_t timestamp_; //DLL TimeStamp
+
+	imported_list imports_;
+};
+
+//Simple import directory rebuilder
+//Class representing import rebuilder advanced settings
+class import_rebuilder_settings
+{
+public:
+	//Default constructor
+	//Default constructor
+	//If set_to_pe_headers = true, IMAGE_DIRECTORY_ENTRY_IMPORT entry will be reset
+	//to new value after import rebuilding
+	//If auto_zero_directory_entry_iat = true, IMAGE_DIRECTORY_ENTRY_IAT will be set to zero
+	//IMAGE_DIRECTORY_ENTRY_IAT is used by loader to temporarily make section, where IMAGE_DIRECTORY_ENTRY_IAT RVA points, writeable
+	//to be able to modify IAT thunks
+	explicit import_rebuilder_settings(bool set_to_pe_headers = true, bool auto_zero_directory_entry_iat = false);
+
+	//Returns offset from section start where import directory data will be placed
+	uint32_t get_offset_from_section_start() const;
+	//Returns true if Original import address table (IAT) will be rebuilt
+	bool build_original_iat() const;
+
+	//Returns true if Original import address and import address tables will not be rebuilt,
+	//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+	bool save_iat_and_original_iat_rvas() const;
+	//Returns true if Original import address and import address tables contents will be rewritten
+	//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+	//and save_iat_and_original_iat_rvas is true
+	bool rewrite_iat_and_original_iat_contents() const;
+
+	//Returns true if original missing IATs will be rebuilt
+	//(only if IATs are saved)
+	bool fill_missing_original_iats() const;
+	//Returns true if PE headers should be updated automatically after rebuilding of imports
+	bool auto_set_to_pe_headers() const;
+	//Returns true if IMAGE_DIRECTORY_ENTRY_IAT must be zeroed, works only if auto_set_to_pe_headers = true
+	bool zero_directory_entry_iat() const;
+
+	//Returns true if the last section should be stripped automatically, if imports are inside it
+	bool auto_strip_last_section_enabled() const;
+
+public: //Setters
+	//Sets offset from section start where import directory data will be placed
+	void set_offset_from_section_start(uint32_t offset);
+	//Sets if Original import address table (IAT) will be rebuilt
+	void build_original_iat(bool enable);
+	//Sets if Original import address and import address tables will not be rebuilt,
+	//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+	//enable_rewrite_iat_and_original_iat_contents sets if Original import address and import address tables contents will be rewritten
+	//works only if import descriptor IAT (and orig.IAT, if present) RVAs are not zero
+	//and save_iat_and_original_iat_rvas is true
+	void save_iat_and_original_iat_rvas(bool enable, bool enable_rewrite_iat_and_original_iat_contents = false);
+	//Sets if original missing IATs will be rebuilt
+	//(only if IATs are saved)
+	void fill_missing_original_iats(bool enable);
+	//Sets if PE headers should be updated automatically after rebuilding of imports
+	void auto_set_to_pe_headers(bool enable);
+	//Sets if IMAGE_DIRECTORY_ENTRY_IAT must be zeroed, works only if auto_set_to_pe_headers = true
+	void zero_directory_entry_iat(bool enable);
+
+	//Sets if the last section should be stripped automatically, if imports are inside it, default true
+	void enable_auto_strip_last_section(bool enable);
+
+private:
+	uint32_t offset_from_section_start_;
+	bool build_original_iat_;
+	bool save_iat_and_original_iat_rvas_;
+	bool fill_missing_original_iats_;
+	bool set_to_pe_headers_;
+	bool zero_directory_entry_iat_;
+	bool rewrite_iat_and_original_iat_contents_;
+	bool auto_strip_last_section_;
+};
+
+typedef std::vector<import_library> imported_functions_list;
+
+
+//Returns imported functions list with related libraries info
+const imported_functions_list get_imported_functions(const pe_base& pe);
+
+template<typename PEClassType>
+const imported_functions_list get_imported_functions_base(const pe_base& pe);
+
+
+//You can get all image imports with get_imported_functions() function
+//You can use returned value to, for example, add new imported library with some functions
+//to the end of list of imported libraries
+//To keep PE file working, rebuild its imports with save_iat_and_original_iat_rvas = true (default)
+//Don't add new imported functions to existing imported library entries, because this can cause
+//rewriting of some used memory (or other IAT/orig.IAT fields) by system loader
+//The safest way is just adding import libraries with functions to the end of imported_functions_list array
+const image_directory rebuild_imports(pe_base& pe, const imported_functions_list& imports, section& import_section, const import_rebuilder_settings& import_settings = import_rebuilder_settings());
+
+template<typename PEClassType>
+const image_directory rebuild_imports_base(pe_base& pe, const imported_functions_list& imports, section& import_section, const import_rebuilder_settings& import_settings = import_rebuilder_settings());
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcproj b/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..783912c0254e9a959cc0fbd342c96911de9115f0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcproj
@@ -0,0 +1,639 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="pe_bliss"
+	ProjectGUID="{4B658F8F-1722-4EEA-880C-A4A64DCA9F2C}"
+	RootNamespace="pe_bliss"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="4"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				PreprocessorDefinitions="WIN32;_DEBUG;_LIB"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLibrarianTool"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="4"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_LIB"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLibrarianTool"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="4"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				PreprocessorDefinitions="WIN32;NDEBUG;_LIB"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLibrarianTool"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="4"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_LIB"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLibrarianTool"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\pe_base.cpp"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_exception.cpp"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_factory.cpp"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_properties.cpp"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_properties_generic.cpp"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_rebuilder.cpp"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_section.cpp"
+				>
+			</File>
+			<Filter
+				Name="Other"
+				>
+				<File
+					RelativePath=".\entropy.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_checksum.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_rich_data.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\utils.cpp"
+					>
+				</File>
+			</Filter>
+			<Filter
+				Name="PE Resources"
+				>
+				<File
+					RelativePath=".\file_version_info.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\message_table.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_resource_manager.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_resource_viewer.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_bitmap_reader.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_bitmap_writer.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_cursor_icon_reader.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_cursor_icon_writer.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_data_info.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_message_list_reader.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_string_table_reader.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_version_info_reader.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_version_info_writer.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\version_info_editor.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\version_info_viewer.cpp"
+					>
+				</File>
+			</Filter>
+			<Filter
+				Name="PE Directories"
+				>
+				<File
+					RelativePath=".\pe_bound_import.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_debug.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_directory.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_dotnet.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_exception_directory.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_exports.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_imports.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_load_config.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_relocations.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_resources.cpp"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_tls.cpp"
+					>
+				</File>
+			</Filter>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath=".\pe_base.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_bliss.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_bliss_resources.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_exception.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_factory.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_properties.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_properties_generic.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_rebuilder.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_section.h"
+				>
+			</File>
+			<File
+				RelativePath=".\pe_structures.h"
+				>
+			</File>
+			<File
+				RelativePath=".\stdint_defs.h"
+				>
+			</File>
+			<Filter
+				Name="Other"
+				>
+				<File
+					RelativePath=".\entropy.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_checksum.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_rich_data.h"
+					>
+				</File>
+				<File
+					RelativePath=".\utils.h"
+					>
+				</File>
+			</Filter>
+			<Filter
+				Name="PE Resources"
+				>
+				<File
+					RelativePath=".\file_version_info.h"
+					>
+				</File>
+				<File
+					RelativePath=".\message_table.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_resource_manager.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_resource_viewer.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_bitmap_reader.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_bitmap_writer.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_cursor_icon_reader.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_cursor_icon_writer.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_data_info.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_internal.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_message_list_reader.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_string_table_reader.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_version_info_reader.h"
+					>
+				</File>
+				<File
+					RelativePath=".\resource_version_info_writer.h"
+					>
+				</File>
+				<File
+					RelativePath=".\version_info_editor.h"
+					>
+				</File>
+				<File
+					RelativePath=".\version_info_viewer.h"
+					>
+				</File>
+			</Filter>
+			<Filter
+				Name="PE Directories"
+				>
+				<File
+					RelativePath=".\pe_bound_import.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_debug.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_directory.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_dotnet.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_exception_directory.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_exports.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_imports.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_load_config.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_relocations.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_resources.h"
+					>
+				</File>
+				<File
+					RelativePath=".\pe_tls.h"
+					>
+				</File>
+			</Filter>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+		<File
+			RelativePath=".\readme.txt"
+			>
+		</File>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcxproj b/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..845bf5c35e83f572c0ff5aa33c4d319c6c14d768
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcxproj
@@ -0,0 +1,228 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="entropy.cpp" />
+    <ClCompile Include="file_version_info.cpp" />
+    <ClCompile Include="message_table.cpp" />
+    <ClCompile Include="pe_bound_import.cpp" />
+    <ClCompile Include="pe_checksum.cpp" />
+    <ClCompile Include="pe_directory.cpp" />
+    <ClCompile Include="pe_load_config.cpp" />
+    <ClCompile Include="pe_properties.cpp" />
+    <ClCompile Include="pe_properties_generic.cpp" />
+    <ClCompile Include="pe_rebuilder.cpp" />
+    <ClCompile Include="pe_resource_viewer.cpp" />
+    <ClCompile Include="pe_section.cpp" />
+    <ClCompile Include="pe_tls.cpp" />
+    <ClCompile Include="pe_debug.cpp" />
+    <ClCompile Include="pe_dotnet.cpp" />
+    <ClCompile Include="pe_exception_directory.cpp" />
+    <ClCompile Include="pe_exports.cpp" />
+    <ClCompile Include="pe_imports.cpp" />
+    <ClCompile Include="pe_base.cpp" />
+    <ClCompile Include="pe_exception.cpp" />
+    <ClCompile Include="pe_factory.cpp" />
+    <ClCompile Include="pe_resource_manager.cpp" />
+    <ClCompile Include="pe_relocations.cpp" />
+    <ClCompile Include="pe_resources.cpp" />
+    <ClCompile Include="pe_rich_data.cpp" />
+    <ClCompile Include="resource_bitmap_reader.cpp" />
+    <ClCompile Include="resource_bitmap_writer.cpp" />
+    <ClCompile Include="resource_cursor_icon_writer.cpp" />
+    <ClCompile Include="resource_data_info.cpp" />
+    <ClCompile Include="resource_cursor_icon_reader.cpp" />
+    <ClCompile Include="resource_message_list_reader.cpp" />
+    <ClCompile Include="resource_string_table_reader.cpp" />
+    <ClCompile Include="resource_version_info_reader.cpp" />
+    <ClCompile Include="resource_version_info_writer.cpp" />
+    <ClCompile Include="utils.cpp" />
+    <ClCompile Include="version_info_editor.cpp" />
+    <ClCompile Include="version_info_viewer.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="entropy.h" />
+    <ClInclude Include="file_version_info.h" />
+    <ClInclude Include="message_table.h" />
+    <ClInclude Include="pe_bliss_resources.h" />
+    <ClInclude Include="pe_bound_import.h" />
+    <ClInclude Include="pe_checksum.h" />
+    <ClInclude Include="pe_debug.h" />
+    <ClInclude Include="pe_directory.h" />
+    <ClInclude Include="pe_dotnet.h" />
+    <ClInclude Include="pe_exception_directory.h" />
+    <ClInclude Include="pe_exports.h" />
+    <ClInclude Include="pe_imports.h" />
+    <ClInclude Include="pe_base.h" />
+    <ClInclude Include="pe_bliss.h" />
+    <ClInclude Include="pe_exception.h" />
+    <ClInclude Include="pe_factory.h" />
+    <ClInclude Include="pe_load_config.h" />
+    <ClInclude Include="pe_properties.h" />
+    <ClInclude Include="pe_properties_generic.h" />
+    <ClInclude Include="pe_rebuilder.h" />
+    <ClInclude Include="pe_resource_manager.h" />
+    <ClInclude Include="pe_resource_viewer.h" />
+    <ClInclude Include="pe_section.h" />
+    <ClInclude Include="pe_structures.h" />
+    <ClInclude Include="pe_relocations.h" />
+    <ClInclude Include="pe_resources.h" />
+    <ClInclude Include="pe_rich_data.h" />
+    <ClInclude Include="pe_tls.h" />
+    <ClInclude Include="resource_bitmap_reader.h" />
+    <ClInclude Include="resource_bitmap_writer.h" />
+    <ClInclude Include="resource_data_info.h" />
+    <ClInclude Include="resource_cursor_icon_reader.h" />
+    <ClInclude Include="resource_cursor_icon_writer.h" />
+    <ClInclude Include="resource_internal.h" />
+    <ClInclude Include="resource_message_list_reader.h" />
+    <ClInclude Include="resource_string_table_reader.h" />
+    <ClInclude Include="resource_version_info_reader.h" />
+    <ClInclude Include="resource_version_info_writer.h" />
+    <ClInclude Include="stdint_defs.h" />
+    <ClInclude Include="utils.h" />
+    <ClInclude Include="version_info_editor.h" />
+    <ClInclude Include="version_info_types.h" />
+    <ClInclude Include="version_info_viewer.h" />
+  </ItemGroup>
+  <ItemGroup>
+    <None Include="readme.txt" />
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{1461F543-D1FA-4E4C-B6D7-0F879F566035}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>pe_bliss</RootNamespace>
+    <ProjectName>pe_bliss</ProjectName>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>StaticLibrary</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>StaticLibrary</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>StaticLibrary</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>StaticLibrary</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Windows</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcxproj.filters b/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..0cb924dcf10d505851d8d888dc90f7bf935564d0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_lib.vcxproj.filters
@@ -0,0 +1,282 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+    <Filter Include="Header Files\Other">
+      <UniqueIdentifier>{a442c791-435d-43d3-9545-28196fb75dd9}</UniqueIdentifier>
+    </Filter>
+    <Filter Include="Header Files\PE Directories">
+      <UniqueIdentifier>{f1eddfb5-ad88-4a6f-8516-031af6cbcff1}</UniqueIdentifier>
+    </Filter>
+    <Filter Include="Header Files\PE Resources">
+      <UniqueIdentifier>{5e3db017-30ee-4ba1-878c-9e1fe4155555}</UniqueIdentifier>
+    </Filter>
+    <Filter Include="Source Files\PE Resources">
+      <UniqueIdentifier>{9f2f9f68-41ae-41a6-b8ae-74eb7b966c8f}</UniqueIdentifier>
+    </Filter>
+    <Filter Include="Source Files\Other">
+      <UniqueIdentifier>{58541054-25c2-412f-93c4-c6f3d8da7c70}</UniqueIdentifier>
+    </Filter>
+    <Filter Include="Source Files\PE Directories">
+      <UniqueIdentifier>{8429c41b-f602-42fb-994f-0fa4ee6f0601}</UniqueIdentifier>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="pe_base.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_exception.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_factory.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_section.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_debug.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_directory.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_dotnet.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_exception_directory.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_exports.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_imports.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_load_config.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_relocations.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_resources.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_tls.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_resource_manager.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_rich_data.cpp">
+      <Filter>Source Files\Other</Filter>
+    </ClCompile>
+    <ClCompile Include="entropy.cpp">
+      <Filter>Source Files\Other</Filter>
+    </ClCompile>
+    <ClCompile Include="utils.cpp">
+      <Filter>Source Files\Other</Filter>
+    </ClCompile>
+    <ClCompile Include="message_table.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="file_version_info.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="version_info_viewer.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="version_info_editor.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_resource_viewer.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_properties_generic.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_properties.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_checksum.cpp">
+      <Filter>Source Files\Other</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_bound_import.cpp">
+      <Filter>Source Files\PE Directories</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_data_info.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_bitmap_reader.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_bitmap_writer.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_cursor_icon_reader.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_cursor_icon_writer.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_version_info_reader.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_version_info_writer.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_string_table_reader.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="resource_message_list_reader.cpp">
+      <Filter>Source Files\PE Resources</Filter>
+    </ClCompile>
+    <ClCompile Include="pe_rebuilder.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="pe_base.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_exception.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_factory.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_structures.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="stdint_defs.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_bliss.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_section.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_bound_import.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_debug.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_directory.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_dotnet.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_exception_directory.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_exports.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_imports.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_relocations.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_resources.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_tls.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_load_config.h">
+      <Filter>Header Files\PE Directories</Filter>
+    </ClInclude>
+    <ClInclude Include="entropy.h">
+      <Filter>Header Files\Other</Filter>
+    </ClInclude>
+    <ClInclude Include="utils.h">
+      <Filter>Header Files\Other</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_rich_data.h">
+      <Filter>Header Files\Other</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_resource_manager.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="message_table.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="file_version_info.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="version_info_viewer.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_resource_viewer.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="version_info_editor.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_internal.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_properties.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_properties_generic.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_checksum.h">
+      <Filter>Header Files\Other</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_bliss_resources.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_data_info.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_bitmap_reader.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_bitmap_writer.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_cursor_icon_reader.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_cursor_icon_writer.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_version_info_reader.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_version_info_writer.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_string_table_reader.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="resource_message_list_reader.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+    <ClInclude Include="pe_rebuilder.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="version_info_types.h">
+      <Filter>Header Files\PE Resources</Filter>
+    </ClInclude>
+  </ItemGroup>
+  <ItemGroup>
+    <None Include="readme.txt" />
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_load_config.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_load_config.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..dedb2a61a16c4a7b4e9dbd9fa9cda195a9f825de
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_load_config.cpp
@@ -0,0 +1,536 @@
+#include <algorithm>
+#include <string.h>
+#include "pe_load_config.h"
+#include "pe_properties_generic.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//IMAGE CONFIG
+//Default constructor
+image_config_info::image_config_info()
+	:time_stamp_(0),
+	major_version_(0), minor_version_(0),
+	global_flags_clear_(0), global_flags_set_(0),
+	critical_section_default_timeout_(0),
+	decommit_free_block_threshold_(0), decommit_total_free_threshold_(0),
+	lock_prefix_table_va_(0),
+	max_allocation_size_(0),
+	virtual_memory_threshold_(0),
+	process_affinity_mask_(0),
+	process_heap_flags_(0),
+	service_pack_version_(0),
+	edit_list_va_(0),
+	security_cookie_va_(0),
+	se_handler_table_va_(0),
+	se_handler_count_(0)
+{}
+
+//Constructors from PE structures
+template<typename ConfigStructure>
+image_config_info::image_config_info(const ConfigStructure& info)
+	:time_stamp_(info.TimeDateStamp),
+	major_version_(info.MajorVersion), minor_version_(info.MinorVersion),
+	global_flags_clear_(info.GlobalFlagsClear), global_flags_set_(info.GlobalFlagsSet),
+	critical_section_default_timeout_(info.CriticalSectionDefaultTimeout),
+	decommit_free_block_threshold_(info.DeCommitFreeBlockThreshold), decommit_total_free_threshold_(info.DeCommitTotalFreeThreshold),
+	lock_prefix_table_va_(info.LockPrefixTable),
+	max_allocation_size_(info.MaximumAllocationSize),
+	virtual_memory_threshold_(info.VirtualMemoryThreshold),
+	process_affinity_mask_(info.ProcessAffinityMask),
+	process_heap_flags_(info.ProcessHeapFlags),
+	service_pack_version_(info.CSDVersion),
+	edit_list_va_(info.EditList),
+	security_cookie_va_(info.SecurityCookie),
+	se_handler_table_va_(info.SEHandlerTable),
+	se_handler_count_(info.SEHandlerCount)
+{}
+
+//Instantiate template constructor with needed structures
+template image_config_info::image_config_info(const image_load_config_directory32& info);
+template image_config_info::image_config_info(const image_load_config_directory64& info);
+
+//Returns the date and time stamp value
+uint32_t image_config_info::get_time_stamp() const
+{
+	return time_stamp_;
+}
+
+//Returns major version number
+uint16_t image_config_info::get_major_version() const
+{
+	return major_version_;
+}
+
+//Returns minor version number
+uint16_t image_config_info::get_minor_version() const
+{
+	return minor_version_;
+}
+
+//Returns clear global flags
+uint32_t image_config_info::get_global_flags_clear() const
+{
+	return global_flags_clear_;
+}
+
+//Returns set global flags
+uint32_t image_config_info::get_global_flags_set() const
+{
+	return global_flags_set_;
+}
+
+//Returns critical section default timeout
+uint32_t image_config_info::get_critical_section_default_timeout() const
+{
+	return critical_section_default_timeout_;
+}
+
+//Get the size of the minimum block that
+//must be freed before it is freed (de-committed), in bytes
+uint64_t image_config_info::get_decommit_free_block_threshold() const
+{
+	return decommit_free_block_threshold_;
+}
+
+//Returns the size of the minimum total memory
+//that must be freed in the process heap before it is freed (de-committed), in bytes
+uint64_t image_config_info::get_decommit_total_free_threshold() const
+{
+	return decommit_total_free_threshold_;
+}
+
+//Returns VA of a list of addresses where the LOCK prefix is used
+uint64_t image_config_info::get_lock_prefix_table_va() const
+{
+	return lock_prefix_table_va_;
+}
+
+//Returns the maximum allocation size, in bytes
+uint64_t image_config_info::get_max_allocation_size() const
+{
+	return max_allocation_size_;
+}
+
+//Returns the maximum block size that can be allocated from heap segments, in bytes
+uint64_t image_config_info::get_virtual_memory_threshold() const
+{
+	return virtual_memory_threshold_;
+}
+
+//Returns process affinity mask
+uint64_t image_config_info::get_process_affinity_mask() const
+{
+	return process_affinity_mask_;
+}
+
+//Returns process heap flags
+uint32_t image_config_info::get_process_heap_flags() const
+{
+	return process_heap_flags_;
+}
+
+//Returns service pack version (CSDVersion)
+uint16_t image_config_info::get_service_pack_version() const
+{
+	return service_pack_version_;
+}
+
+//Returns VA of edit list (reserved by system)
+uint64_t image_config_info::get_edit_list_va() const
+{
+	return edit_list_va_;
+}
+
+//Returns a pointer to a cookie that is used by Visual C++ or GS implementation
+uint64_t image_config_info::get_security_cookie_va() const
+{
+	return security_cookie_va_;
+}
+
+//Returns VA of the sorted table of RVAs of each valid, unique handler in the image
+uint64_t image_config_info::get_se_handler_table_va() const
+{
+	return se_handler_table_va_;
+}
+
+//Returns the count of unique handlers in the table
+uint64_t image_config_info::get_se_handler_count() const
+{
+	return se_handler_count_;
+}
+
+//Returns SE Handler RVA list
+const image_config_info::se_handler_list& image_config_info::get_se_handler_rvas() const
+{
+	return se_handlers_;
+}
+
+//Returns Lock Prefix RVA list
+const image_config_info::lock_prefix_rva_list& image_config_info::get_lock_prefix_rvas() const
+{
+	return lock_prefixes_;
+}
+
+//Adds SE Handler RVA to list
+void image_config_info::add_se_handler_rva(uint32_t rva)
+{
+	se_handlers_.push_back(rva);
+}
+
+//Clears SE Handler list
+void image_config_info::clear_se_handler_list()
+{
+	se_handlers_.clear();
+}
+
+//Adds Lock Prefix RVA to list
+void image_config_info::add_lock_prefix_rva(uint32_t rva)
+{
+	lock_prefixes_.push_back(rva);
+}
+
+//Clears Lock Prefix list
+void image_config_info::clear_lock_prefix_list()
+{
+	lock_prefixes_.clear();
+}
+
+//Sets the date and time stamp value
+void image_config_info::set_time_stamp(uint32_t time_stamp)
+{
+	time_stamp_ = time_stamp;
+}
+
+//Sets major version number
+void image_config_info::set_major_version(uint16_t major_version)
+{
+	major_version_ = major_version;
+}
+
+//Sets minor version number
+void image_config_info::set_minor_version(uint16_t minor_version)
+{
+	minor_version_ = minor_version;
+}
+
+//Sets clear global flags
+void image_config_info::set_global_flags_clear(uint32_t global_flags_clear)
+{
+	global_flags_clear_ = global_flags_clear;
+}
+
+//Sets set global flags
+void image_config_info::set_global_flags_set(uint32_t global_flags_set)
+{
+	global_flags_set_ = global_flags_set;
+}
+
+//Sets critical section default timeout
+void image_config_info::set_critical_section_default_timeout(uint32_t critical_section_default_timeout)
+{
+	critical_section_default_timeout_ = critical_section_default_timeout;
+}
+
+//Sets the size of the minimum block that
+//must be freed before it is freed (de-committed), in bytes
+void image_config_info::set_decommit_free_block_threshold(uint64_t decommit_free_block_threshold)
+{
+	decommit_free_block_threshold_ = decommit_free_block_threshold;
+}
+
+//Sets the size of the minimum total memory
+//that must be freed in the process heap before it is freed (de-committed), in bytes
+void image_config_info::set_decommit_total_free_threshold(uint64_t decommit_total_free_threshold)
+{
+	decommit_total_free_threshold_ = decommit_total_free_threshold;
+}
+
+//Sets VA of a list of addresses where the LOCK prefix is used
+//If you rebuild this list, VA will be re-assigned automatically
+void image_config_info::set_lock_prefix_table_va(uint64_t lock_prefix_table_va)
+{
+	lock_prefix_table_va_ = lock_prefix_table_va;
+}
+
+//Sets the maximum allocation size, in bytes
+void image_config_info::set_max_allocation_size(uint64_t max_allocation_size)
+{
+	max_allocation_size_ = max_allocation_size;
+}
+
+//Sets the maximum block size that can be allocated from heap segments, in bytes
+void image_config_info::set_virtual_memory_threshold(uint64_t virtual_memory_threshold)
+{
+	virtual_memory_threshold_ = virtual_memory_threshold;
+}
+
+//Sets process affinity mask
+void image_config_info::set_process_affinity_mask(uint64_t process_affinity_mask)
+{
+	process_affinity_mask_ = process_affinity_mask;
+}
+
+//Sets process heap flags
+void image_config_info::set_process_heap_flags(uint32_t process_heap_flags)
+{
+	process_heap_flags_ = process_heap_flags;
+}
+
+//Sets service pack version (CSDVersion)
+void image_config_info::set_service_pack_version(uint16_t service_pack_version)
+{
+	service_pack_version_ = service_pack_version;
+}
+
+//Sets VA of edit list (reserved by system)
+void image_config_info::set_edit_list_va(uint64_t edit_list_va)
+{
+	edit_list_va_ = edit_list_va;
+}
+
+//Sets a pointer to a cookie that is used by Visual C++ or GS implementation
+void image_config_info::set_security_cookie_va(uint64_t security_cookie_va)
+{
+	security_cookie_va_ = security_cookie_va;
+}
+
+//Sets VA of the sorted table of RVAs of each valid, unique handler in the image
+//If you rebuild this list, VA will be re-assigned automatically
+void image_config_info::set_se_handler_table_va(uint64_t se_handler_table_va)
+{
+	se_handler_table_va_ = se_handler_table_va;
+}
+
+//Returns SE Handler RVA list
+image_config_info::se_handler_list& image_config_info::get_se_handler_rvas()
+{
+	return se_handlers_;
+}
+
+//Returns Lock Prefix RVA list
+image_config_info::lock_prefix_rva_list& image_config_info::get_lock_prefix_rvas()
+{
+	return lock_prefixes_;
+}
+
+//Returns image config info
+//If image does not have config info, throws an exception
+const image_config_info get_image_config(const pe_base& pe)
+{
+	return pe.get_pe_type() == pe_type_32
+		? get_image_config_base<pe_types_class_32>(pe)
+		: get_image_config_base<pe_types_class_64>(pe);
+}
+
+//Image config rebuilder
+const image_directory rebuild_image_config(pe_base& pe, const image_config_info& info, section& image_config_section, uint32_t offset_from_section_start, bool write_se_handlers, bool write_lock_prefixes, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	return pe.get_pe_type() == pe_type_32
+		? rebuild_image_config_base<pe_types_class_32>(pe, info, image_config_section, offset_from_section_start, write_se_handlers, write_lock_prefixes, save_to_pe_header, auto_strip_last_section)
+		: rebuild_image_config_base<pe_types_class_64>(pe, info, image_config_section, offset_from_section_start, write_se_handlers, write_lock_prefixes, save_to_pe_header, auto_strip_last_section);
+}
+
+
+//Returns image config info
+//If image does not have config info, throws an exception
+template<typename PEClassType>
+const image_config_info get_image_config_base(const pe_base& pe)
+{
+	//Check if image has config directory
+	if(!pe.has_config())
+		throw pe_exception("Image does not have load config directory", pe_exception::directory_does_not_exist);
+
+	//Get load config structure
+	typename PEClassType::ConfigStruct config_info = pe.section_data_from_rva<typename PEClassType::ConfigStruct>(pe.get_directory_rva(image_directory_entry_load_config), section_data_virtual);
+
+	//Check size of config directory
+	if(config_info.Size != sizeof(config_info))
+		throw pe_exception("Incorrect (or old) load config directory", pe_exception::incorrect_config_directory);
+
+	//Fill return structure
+	image_config_info ret(config_info);
+
+	//Check possible overflow
+	if(config_info.SEHandlerCount >= pe_utils::max_dword / sizeof(uint32_t)
+		|| config_info.SEHandlerTable >= static_cast<typename PEClassType::BaseSize>(-1) - config_info.SEHandlerCount * sizeof(uint32_t))
+		throw pe_exception("Incorrect load config directory", pe_exception::incorrect_config_directory);
+
+	//Read sorted SE handler RVA list (if any)
+	for(typename PEClassType::BaseSize i = 0; i != config_info.SEHandlerCount; ++i)
+		ret.add_se_handler_rva(pe.section_data_from_va<uint32_t>(static_cast<typename PEClassType::BaseSize>(config_info.SEHandlerTable + i * sizeof(uint32_t))));
+
+	if(config_info.LockPrefixTable)
+	{
+		//Read Lock Prefix VA list (if any)
+		unsigned long current = 0;
+		while(true)
+		{
+			typename PEClassType::BaseSize lock_prefix_va = pe.section_data_from_va<typename PEClassType::BaseSize>(static_cast<typename PEClassType::BaseSize>(config_info.LockPrefixTable + current * sizeof(typename PEClassType::BaseSize)));
+			if(!lock_prefix_va)
+				break;
+
+			ret.add_lock_prefix_rva(pe.va_to_rva(lock_prefix_va));
+
+			++current;
+		}
+	}
+
+	return ret;
+}
+
+//Image config directory rebuilder
+//auto_strip_last_section - if true and TLS are placed in the last section, it will be automatically stripped
+//If write_se_handlers = true, SE Handlers list will be written just after image config directory structure
+//If write_lock_prefixes = true, Lock Prefixes address list will be written just after image config directory structure
+template<typename PEClassType>
+const image_directory rebuild_image_config_base(pe_base& pe, const image_config_info& info, section& image_config_section, uint32_t offset_from_section_start, bool write_se_handlers, bool write_lock_prefixes, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	//Check that image_config_section is attached to this PE image
+	if(!pe.section_attached(image_config_section))
+		throw pe_exception("Image Config section must be attached to PE file", pe_exception::section_is_not_attached);
+	
+	uint32_t alignment = pe_utils::align_up(offset_from_section_start, sizeof(typename PEClassType::BaseSize)) - offset_from_section_start;
+
+	uint32_t needed_size = sizeof(typename PEClassType::ConfigStruct); //Calculate needed size for Image Config table
+	
+	uint32_t image_config_data_pos = offset_from_section_start + alignment;
+
+	uint32_t current_pos_of_se_handlers = 0;
+	uint32_t current_pos_of_lock_prefixes = 0;
+	
+	if(write_se_handlers)
+	{
+		current_pos_of_se_handlers = needed_size + image_config_data_pos;
+		needed_size += static_cast<uint32_t>(info.get_se_handler_rvas().size()) * sizeof(uint32_t); //RVAs of SE Handlers
+	}
+	
+	if(write_lock_prefixes)
+	{
+		current_pos_of_lock_prefixes = needed_size + image_config_data_pos;
+		needed_size += static_cast<uint32_t>((info.get_lock_prefix_rvas().size() + 1) * sizeof(typename PEClassType::BaseSize)); //VAs of Lock Prefixes (and ending null element)
+	}
+
+	//Check if image_config_section is last one. If it's not, check if there's enough place for Image Config data
+	if(&image_config_section != &*(pe.get_image_sections().end() - 1) && 
+		(image_config_section.empty() || pe_utils::align_up(image_config_section.get_size_of_raw_data(), pe.get_file_alignment()) < needed_size + image_config_data_pos))
+		throw pe_exception("Insufficient space for TLS directory", pe_exception::insufficient_space);
+
+	std::string& raw_data = image_config_section.get_raw_data();
+
+	//This will be done only if image_config_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + image_config_data_pos)
+		raw_data.resize(needed_size + image_config_data_pos); //Expand section raw data
+
+	//Create and fill Image Config structure
+	typename PEClassType::ConfigStruct image_config_section_struct = {0};
+	image_config_section_struct.Size = sizeof(image_config_section_struct);
+	image_config_section_struct.TimeDateStamp = info.get_time_stamp();
+	image_config_section_struct.MajorVersion = info.get_major_version();
+	image_config_section_struct.MinorVersion = info.get_minor_version();
+	image_config_section_struct.GlobalFlagsClear = info.get_global_flags_clear();
+	image_config_section_struct.GlobalFlagsSet = info.get_global_flags_set();
+	image_config_section_struct.CriticalSectionDefaultTimeout = info.get_critical_section_default_timeout();
+	image_config_section_struct.DeCommitFreeBlockThreshold = static_cast<typename PEClassType::BaseSize>(info.get_decommit_free_block_threshold());
+	image_config_section_struct.DeCommitTotalFreeThreshold = static_cast<typename PEClassType::BaseSize>(info.get_decommit_total_free_threshold());
+	image_config_section_struct.MaximumAllocationSize = static_cast<typename PEClassType::BaseSize>(info.get_max_allocation_size());
+	image_config_section_struct.VirtualMemoryThreshold = static_cast<typename PEClassType::BaseSize>(info.get_virtual_memory_threshold());
+	image_config_section_struct.ProcessHeapFlags = info.get_process_heap_flags();
+	image_config_section_struct.ProcessAffinityMask = static_cast<typename PEClassType::BaseSize>(info.get_process_affinity_mask());
+	image_config_section_struct.CSDVersion = info.get_service_pack_version();
+	image_config_section_struct.EditList = static_cast<typename PEClassType::BaseSize>(info.get_edit_list_va());
+	image_config_section_struct.SecurityCookie = static_cast<typename PEClassType::BaseSize>(info.get_security_cookie_va());
+	image_config_section_struct.SEHandlerCount = static_cast<typename PEClassType::BaseSize>(info.get_se_handler_rvas().size());
+	
+
+	if(write_se_handlers)
+	{
+		if(info.get_se_handler_rvas().empty())
+		{
+			write_se_handlers = false;
+			image_config_section_struct.SEHandlerTable = 0;
+		}
+		else
+		{
+			typename PEClassType::BaseSize va;
+			pe.rva_to_va(pe.rva_from_section_offset(image_config_section, current_pos_of_se_handlers), va);
+			image_config_section_struct.SEHandlerTable = va;
+		}
+	}
+	else
+	{
+		image_config_section_struct.SEHandlerTable = static_cast<typename PEClassType::BaseSize>(info.get_se_handler_table_va());
+	}
+
+	if(write_lock_prefixes)
+	{
+		if(info.get_lock_prefix_rvas().empty())
+		{
+			write_lock_prefixes = false;
+			image_config_section_struct.LockPrefixTable = 0;
+		}
+		else
+		{
+			typename PEClassType::BaseSize va;
+			pe.rva_to_va(pe.rva_from_section_offset(image_config_section, current_pos_of_lock_prefixes), va);
+			image_config_section_struct.LockPrefixTable = va;
+		}
+	}
+	else
+	{
+		image_config_section_struct.LockPrefixTable = static_cast<typename PEClassType::BaseSize>(info.get_lock_prefix_table_va());
+	}
+
+	//Write image config section
+	memcpy(&raw_data[image_config_data_pos], &image_config_section_struct, sizeof(image_config_section_struct));
+
+	if(write_se_handlers)
+	{
+		//Sort SE Handlers list
+		image_config_info::se_handler_list sorted_list = info.get_se_handler_rvas();
+		std::sort(sorted_list.begin(), sorted_list.end());
+
+		//Write SE Handlers table
+		for(image_config_info::se_handler_list::const_iterator it = sorted_list.begin(); it != sorted_list.end(); ++it)
+		{
+			uint32_t se_handler_rva = *it;
+			memcpy(&raw_data[current_pos_of_se_handlers], &se_handler_rva, sizeof(se_handler_rva));
+			current_pos_of_se_handlers += sizeof(se_handler_rva);
+		}
+	}
+
+	if(write_lock_prefixes)
+	{
+		//Write Lock Prefixes VA list
+		for(image_config_info::lock_prefix_rva_list::const_iterator it = info.get_lock_prefix_rvas().begin(); it != info.get_lock_prefix_rvas().end(); ++it)
+		{
+			typename PEClassType::BaseSize lock_prefix_va;
+			pe.rva_to_va(*it, lock_prefix_va);
+			memcpy(&raw_data[current_pos_of_lock_prefixes], &lock_prefix_va, sizeof(lock_prefix_va));
+			current_pos_of_lock_prefixes += sizeof(lock_prefix_va);
+		}
+
+		{
+			//Ending null VA
+			typename PEClassType::BaseSize lock_prefix_va = 0;
+			memcpy(&raw_data[current_pos_of_lock_prefixes], &lock_prefix_va, sizeof(lock_prefix_va));
+		}
+	}
+
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(image_config_section, auto_strip_last_section);
+
+	image_directory ret(pe.rva_from_section_offset(image_config_section, image_config_data_pos), sizeof(typename PEClassType::ConfigStruct));
+
+	//If auto-rewrite of PE headers is required
+	if(save_to_pe_header)
+	{
+		pe.set_directory_rva(image_directory_entry_load_config, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_load_config, ret.get_size());
+	}
+
+	return ret;
+}
+
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_load_config.h b/irdb-lib/pebliss/trunk/pe_lib/pe_load_config.h
new file mode 100644
index 0000000000000000000000000000000000000000..5fb6b96c90a834a7252f88f1bd71bbad54ae29a9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_load_config.h
@@ -0,0 +1,166 @@
+#ifndef pebliss_pe_load_config_h
+#define pebliss_pe_load_config_h
+#pragma once
+#include <vector>
+#include "pe_structures.h"
+#include "pe_base.h"
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Class representing image configuration information
+class image_config_info
+{
+public:
+	typedef std::vector<uint32_t> se_handler_list;
+	typedef std::vector<uint32_t> lock_prefix_rva_list;
+
+public:
+	//Default constructor
+	image_config_info();
+	//Constructors from PE structures (no checks)
+	template<typename ConfigStructure>
+	explicit image_config_info(const ConfigStructure& info);
+
+	//Returns the date and time stamp value
+	uint32_t get_time_stamp() const;
+	//Returns major version number
+	uint16_t get_major_version() const;
+	//Returns minor version number
+	uint16_t get_minor_version() const;
+	//Returns clear global flags
+	uint32_t get_global_flags_clear() const;
+	//Returns set global flags
+	uint32_t get_global_flags_set() const;
+	//Returns critical section default timeout
+	uint32_t get_critical_section_default_timeout() const;
+	//Get the size of the minimum block that
+	//must be freed before it is freed (de-committed), in bytes
+	uint64_t get_decommit_free_block_threshold() const;
+	//Returns the size of the minimum total memory
+	//that must be freed in the process heap before it is freed (de-committed), in bytes
+	uint64_t get_decommit_total_free_threshold() const;
+	//Returns VA of a list of addresses where the LOCK prefix is used
+	uint64_t get_lock_prefix_table_va() const;
+	//Returns the maximum allocation size, in bytes
+	uint64_t get_max_allocation_size() const;
+	//Returns the maximum block size that can be allocated from heap segments, in bytes
+	uint64_t get_virtual_memory_threshold() const;
+	//Returns process affinity mask
+	uint64_t get_process_affinity_mask() const;
+	//Returns process heap flags
+	uint32_t get_process_heap_flags() const;
+	//Returns service pack version (CSDVersion)
+	uint16_t get_service_pack_version() const;
+	//Returns VA of edit list (reserved by system)
+	uint64_t get_edit_list_va() const;
+	//Returns a pointer to a cookie that is used by Visual C++ or GS implementation
+	uint64_t get_security_cookie_va() const;
+	//Returns VA of the sorted table of RVAs of each valid, unique handler in the image
+	uint64_t get_se_handler_table_va() const;
+	//Returns the count of unique handlers in the table
+	uint64_t get_se_handler_count() const;
+
+	//Returns SE Handler RVA list
+	const se_handler_list& get_se_handler_rvas() const;
+		
+	//Returns Lock Prefix RVA list
+	const lock_prefix_rva_list& get_lock_prefix_rvas() const;
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//Also you can use these functions to rebuild image config directory
+
+	//Adds SE Handler RVA to list
+	void add_se_handler_rva(uint32_t rva);
+	//Clears SE Handler list
+	void clear_se_handler_list();
+		
+	//Adds Lock Prefix RVA to list
+	void add_lock_prefix_rva(uint32_t rva);
+	//Clears Lock Prefix list
+	void clear_lock_prefix_list();
+		
+	//Sets the date and time stamp value
+	void set_time_stamp(uint32_t time_stamp);
+	//Sets major version number
+	void set_major_version(uint16_t major_version);
+	//Sets minor version number
+	void set_minor_version(uint16_t minor_version);
+	//Sets clear global flags
+	void set_global_flags_clear(uint32_t global_flags_clear);
+	//Sets set global flags
+	void set_global_flags_set(uint32_t global_flags_set);
+	//Sets critical section default timeout
+	void set_critical_section_default_timeout(uint32_t critical_section_default_timeout);
+	//Sets the size of the minimum block that
+	//must be freed before it is freed (de-committed), in bytes
+	void set_decommit_free_block_threshold(uint64_t decommit_free_block_threshold);
+	//Sets the size of the minimum total memory
+	//that must be freed in the process heap before it is freed (de-committed), in bytes
+	void set_decommit_total_free_threshold(uint64_t decommit_total_free_threshold);
+	//Sets VA of a list of addresses where the LOCK prefix is used
+	//If you rebuild this list, VA will be re-assigned automatically
+	void set_lock_prefix_table_va(uint64_t lock_prefix_table_va);
+	//Sets the maximum allocation size, in bytes
+	void set_max_allocation_size(uint64_t max_allocation_size);
+	//Sets the maximum block size that can be allocated from heap segments, in bytes
+	void set_virtual_memory_threshold(uint64_t virtual_memory_threshold);
+	//Sets process affinity mask
+	void set_process_affinity_mask(uint64_t process_affinity_mask);
+	//Sets process heap flags
+	void set_process_heap_flags(uint32_t process_heap_flags);
+	//Sets service pack version (CSDVersion)
+	void set_service_pack_version(uint16_t service_pack_version);
+	//Sets VA of edit list (reserved by system)
+	void set_edit_list_va(uint64_t edit_list_va);
+	//Sets a pointer to a cookie that is used by Visual C++ or GS implementation
+	void set_security_cookie_va(uint64_t security_cookie_va);
+	//Sets VA of the sorted table of RVAs of each valid, unique handler in the image
+	//If you rebuild this list, VA will be re-assigned automatically
+	void set_se_handler_table_va(uint64_t se_handler_table_va);
+
+	//Returns SE Handler RVA list
+	se_handler_list& get_se_handler_rvas();
+
+	//Returns Lock Prefix RVA list
+	lock_prefix_rva_list& get_lock_prefix_rvas();
+
+private:
+	uint32_t time_stamp_;
+	uint16_t major_version_, minor_version_;
+	uint32_t global_flags_clear_, global_flags_set_;
+	uint32_t critical_section_default_timeout_;
+	uint64_t decommit_free_block_threshold_, decommit_total_free_threshold_;
+	uint64_t lock_prefix_table_va_;
+	uint64_t max_allocation_size_;
+	uint64_t virtual_memory_threshold_;
+	uint64_t process_affinity_mask_;
+	uint32_t process_heap_flags_;
+	uint16_t service_pack_version_;
+	uint64_t edit_list_va_;
+	uint64_t security_cookie_va_;
+	uint64_t se_handler_table_va_;
+	uint64_t se_handler_count_;
+
+	se_handler_list se_handlers_;
+	lock_prefix_rva_list lock_prefixes_;
+};
+
+//Returns image config info
+//If image does not have config info, throws an exception
+const image_config_info get_image_config(const pe_base& pe);
+
+template<typename PEClassType>
+const image_config_info get_image_config_base(const pe_base& pe);
+
+
+//Image config directory rebuilder
+//auto_strip_last_section - if true and TLS are placed in the last section, it will be automatically stripped
+//If write_se_handlers = true, SE Handlers list will be written just after image config directory structure
+//If write_lock_prefixes = true, Lock Prefixes address list will be written just after image config directory structure
+const image_directory rebuild_image_config(pe_base& pe, const image_config_info& info, section& image_config_section, uint32_t offset_from_section_start = 0, bool write_se_handlers = true, bool write_lock_prefixes = true, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+
+template<typename PEClassType>
+const image_directory rebuild_image_config_base(pe_base& pe, const image_config_info& info, section& image_config_section, uint32_t offset_from_section_start = 0, bool write_se_handlers = true, bool write_lock_prefixes = true, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_properties.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_properties.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..134bf29caf048f357a8af5c49d503f9a36aeddb3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_properties.cpp
@@ -0,0 +1,20 @@
+#include "pe_properties.h"
+
+namespace pe_bliss
+{
+//Destructor
+pe_properties::~pe_properties()
+{}
+
+//Clears PE characteristics flag
+void pe_properties::clear_characteristics_flags(uint16_t flags)
+{
+	set_characteristics(get_characteristics() & ~flags);
+}
+
+//Sets PE characteristics flag
+void pe_properties::set_characteristics_flags(uint16_t flags)
+{
+	set_characteristics(get_characteristics() | flags);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_properties.h b/irdb-lib/pebliss/trunk/pe_lib/pe_properties.h
new file mode 100644
index 0000000000000000000000000000000000000000..f878045f615a93498a803f26b9d2ba5dbfe67e20
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_properties.h
@@ -0,0 +1,221 @@
+#ifndef pebliss_pe_properties_h
+#define pebliss_pe_properties_h
+#pragma once
+#ifndef pebliss_props_h
+#define pebliss_props_h
+#include <memory>
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+class pe_properties
+{
+public: //Constructors
+	virtual std::auto_ptr<pe_properties> duplicate() const = 0;
+	
+	//Fills properly PE structures
+	virtual void create_pe(uint32_t section_alignment, uint16_t subsystem) = 0;
+
+public:
+	//Destructor
+	virtual ~pe_properties();
+
+
+public: //DIRECTORIES
+	//Returns true if directory exists
+	virtual bool directory_exists(uint32_t id) const = 0;
+
+	//Removes directory
+	virtual void remove_directory(uint32_t id) = 0;
+
+	//Returns directory RVA
+	virtual uint32_t get_directory_rva(uint32_t id) const = 0;
+	//Returns directory size
+	virtual uint32_t get_directory_size(uint32_t id) const = 0;
+
+	//Sets directory RVA (just a value of PE header, no moving occurs)
+	virtual void set_directory_rva(uint32_t id, uint32_t rva) = 0;
+	//Sets directory size (just a value of PE header, no moving occurs)
+	virtual void set_directory_size(uint32_t id, uint32_t size) = 0;
+	
+	//Strips only zero DATA_DIRECTORY entries to count = min_count
+	//Returns resulting number of data directories
+	//strip_iat_directory - if true, even not empty IAT directory will be stripped
+	virtual uint32_t strip_data_directories(uint32_t min_count = 1, bool strip_iat_directory = true) = 0;
+
+
+public: //IMAGE
+	//Returns PE type of this image
+	virtual pe_type get_pe_type() const = 0;
+
+
+public: //PE HEADER
+	//Returns image base for PE32 and PE64 respectively
+	virtual uint32_t get_image_base_32() const = 0;
+	virtual uint64_t get_image_base_64() const = 0;
+
+	//Sets new image base for PE32
+	virtual void set_image_base(uint32_t base) = 0;
+	//Sets new image base for PE32/PE+
+	virtual void set_image_base_64(uint64_t base) = 0;
+
+	//Returns image entry point
+	virtual uint32_t get_ep() const = 0;
+	//Sets image entry point
+	virtual void set_ep(uint32_t new_ep) = 0;
+
+	//Returns file alignment
+	virtual uint32_t get_file_alignment() const = 0;
+	//Returns section alignment
+	virtual uint32_t get_section_alignment() const = 0;
+
+	//Sets heap size commit for PE32 and PE64 respectively
+	virtual void set_heap_size_commit(uint32_t size) = 0;
+	virtual void set_heap_size_commit(uint64_t size) = 0;
+	//Sets heap size reserve for PE32 and PE64 respectively
+	virtual void set_heap_size_reserve(uint32_t size) = 0;
+	virtual void set_heap_size_reserve(uint64_t size) = 0;
+	//Sets stack size commit for PE32 and PE64 respectively
+	virtual void set_stack_size_commit(uint32_t size) = 0;
+	virtual void set_stack_size_commit(uint64_t size) = 0;
+	//Sets stack size reserve for PE32 and PE64 respectively
+	virtual void set_stack_size_reserve(uint32_t size) = 0;
+	virtual void set_stack_size_reserve(uint64_t size) = 0;
+	
+	//Returns heap size commit for PE32 and PE64 respectively
+	virtual uint32_t get_heap_size_commit_32() const = 0;
+	virtual uint64_t get_heap_size_commit_64() const = 0;
+	//Returns heap size reserve for PE32 and PE64 respectively
+	virtual uint32_t get_heap_size_reserve_32() const = 0;
+	virtual uint64_t get_heap_size_reserve_64() const = 0;
+	//Returns stack size commit for PE32 and PE64 respectively
+	virtual uint32_t get_stack_size_commit_32() const = 0;
+	virtual uint64_t get_stack_size_commit_64() const = 0;
+	//Returns stack size reserve for PE32 and PE64 respectively
+	virtual uint32_t get_stack_size_reserve_32() const = 0;
+	virtual uint64_t get_stack_size_reserve_64() const = 0;
+
+	//Returns virtual size of image
+	virtual uint32_t get_size_of_image() const = 0;
+
+	//Returns number of RVA and sizes (number of DATA_DIRECTORY entries)
+	virtual uint32_t get_number_of_rvas_and_sizes() const = 0;
+	//Sets number of RVA and sizes (number of DATA_DIRECTORY entries)
+	virtual void set_number_of_rvas_and_sizes(uint32_t number) = 0;
+
+	//Returns PE characteristics
+	virtual uint16_t get_characteristics() const = 0;
+	//Sets PE characteristics
+	virtual void set_characteristics(uint16_t ch) = 0;
+	
+	//Clears PE characteristics flag
+	void clear_characteristics_flags(uint16_t flags);
+	//Sets PE characteristics flag
+	void set_characteristics_flags(uint16_t flags);
+
+	//Returns size of headers
+	virtual uint32_t get_size_of_headers() const = 0;
+
+	//Returns subsystem
+	virtual uint16_t get_subsystem() const = 0;
+
+	//Sets subsystem
+	virtual void set_subsystem(uint16_t subsystem) = 0;
+
+	//Returns size of optional header
+	virtual uint16_t get_size_of_optional_header() const = 0;
+
+	//Returns PE signature
+	virtual uint32_t get_pe_signature() const = 0;
+
+	//Returns PE magic value
+	virtual uint32_t get_magic() const = 0;
+
+	//Returns checksum of PE file from header
+	virtual uint32_t get_checksum() const = 0;
+	
+	//Sets checksum of PE file
+	virtual void set_checksum(uint32_t checksum) = 0;
+	
+	//Returns timestamp of PE file from header
+	virtual uint32_t get_time_date_stamp() const = 0;
+	
+	//Sets timestamp of PE file
+	virtual void set_time_date_stamp(uint32_t timestamp) = 0;
+	
+	//Returns Machine field value of PE file from header
+	virtual uint16_t get_machine() const = 0;
+
+	//Sets Machine field value of PE file
+	virtual void set_machine(uint16_t machine) = 0;
+
+	//Returns DLL Characteristics
+	virtual uint16_t get_dll_characteristics() const = 0;
+	
+	//Sets DLL Characteristics
+	virtual void set_dll_characteristics(uint16_t characteristics) = 0;
+	
+	//Sets required operation system version
+	virtual void set_os_version(uint16_t major, uint16_t minor) = 0;
+
+	//Returns required operation system version (minor word)
+	virtual uint16_t get_minor_os_version() const = 0;
+
+	//Returns required operation system version (major word)
+	virtual uint16_t get_major_os_version() const = 0;
+
+	//Sets required subsystem version
+	virtual void set_subsystem_version(uint16_t major, uint16_t minor) = 0;
+
+	//Returns required subsystem version (minor word)
+	virtual uint16_t get_minor_subsystem_version() const = 0;
+
+	//Returns required subsystem version (major word)
+	virtual uint16_t get_major_subsystem_version() const = 0;
+
+public: //ADDRESS CONVERTIONS
+	//Virtual Address (VA) to Relative Virtual Address (RVA) convertions
+	//for PE32 and PE64 respectively
+	//bound_check checks integer overflow
+	virtual uint32_t va_to_rva(uint32_t va, bool bound_check = true) const = 0;
+	virtual uint32_t va_to_rva(uint64_t va, bool bound_check = true) const = 0;
+	
+	//Relative Virtual Address (RVA) to Virtual Address (VA) convertions
+	//for PE32 and PE64 respectively
+	virtual uint32_t rva_to_va_32(uint32_t rva) const = 0;
+	virtual uint64_t rva_to_va_64(uint32_t rva) const = 0;
+
+
+public: //SECTIONS
+	//Returns number of sections
+	virtual uint16_t get_number_of_sections() const = 0;
+	
+public:
+	//Sets number of sections
+	virtual void set_number_of_sections(uint16_t number) = 0;
+	//Sets virtual size of image
+	virtual void set_size_of_image(uint32_t size) = 0;
+	//Sets size of headers
+	virtual void set_size_of_headers(uint32_t size) = 0;
+	//Sets size of optional headers
+	virtual void set_size_of_optional_header(uint16_t size) = 0;
+	//Returns nt headers data pointer
+	virtual char* get_nt_headers_ptr() = 0;
+	//Returns nt headers data pointer
+	virtual const char* get_nt_headers_ptr() const = 0;
+	//Returns size of NT header
+	virtual uint32_t get_sizeof_nt_header() const = 0;
+	//Returns size of optional headers
+	virtual uint32_t get_sizeof_opt_headers() const = 0;
+	//Sets file alignment (no checks)
+	virtual void set_file_alignment_unchecked(uint32_t alignment) = 0;
+	//Sets base of code
+	virtual void set_base_of_code(uint32_t base) = 0;
+	//Returns base of code
+	virtual uint32_t get_base_of_code() const = 0;
+	//Returns needed PE magic for PE or PE+ (from template parameters)
+	virtual uint32_t get_needed_magic() const = 0;
+};
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_properties_generic.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_properties_generic.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3b1dadd0f949075582731368d9978a797ededb6e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_properties_generic.cpp
@@ -0,0 +1,624 @@
+#include <string.h>
+#include "pe_properties_generic.h"
+#include "pe_exception.h"
+#include "utils.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+	
+//Constructor
+template<typename PEClassType>
+std::auto_ptr<pe_properties> pe_properties_generic<PEClassType>::duplicate() const
+{
+	return std::auto_ptr<pe_properties>(new pe_properties_generic<PEClassType>(*this));
+}
+
+//Fills properly PE structures
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::create_pe(uint32_t section_alignment, uint16_t subsystem)
+{
+	memset(&nt_headers_, 0, sizeof(nt_headers_));
+	nt_headers_.Signature = 0x4550; //"PE"
+	nt_headers_.FileHeader.Machine = 0x14C; //i386
+	nt_headers_.FileHeader.SizeOfOptionalHeader = sizeof(nt_headers_.OptionalHeader);
+	nt_headers_.OptionalHeader.Magic = PEClassType::Id;
+	nt_headers_.OptionalHeader.ImageBase = 0x400000;
+	nt_headers_.OptionalHeader.SectionAlignment = section_alignment;
+	nt_headers_.OptionalHeader.FileAlignment = 0x200;
+	nt_headers_.OptionalHeader.SizeOfHeaders = 1024;
+	nt_headers_.OptionalHeader.Subsystem = subsystem;
+	nt_headers_.OptionalHeader.SizeOfHeapReserve = 0x100000;
+	nt_headers_.OptionalHeader.SizeOfHeapCommit = 0x1000;
+	nt_headers_.OptionalHeader.SizeOfStackReserve = 0x100000;
+	nt_headers_.OptionalHeader.SizeOfStackCommit = 0x1000;
+	nt_headers_.OptionalHeader.NumberOfRvaAndSizes = 0x10;
+}
+
+//Duplicate
+template<typename PEClassType>
+pe_properties_generic<PEClassType>::~pe_properties_generic()
+{}
+
+//Returns true if directory exists
+template<typename PEClassType>
+bool pe_properties_generic<PEClassType>::directory_exists(uint32_t id) const
+{
+	return (nt_headers_.OptionalHeader.NumberOfRvaAndSizes - 1) >= id &&
+		nt_headers_.OptionalHeader.DataDirectory[id].VirtualAddress;
+}
+
+//Removes directory
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::remove_directory(uint32_t id)
+{
+	if(directory_exists(id))
+	{
+		nt_headers_.OptionalHeader.DataDirectory[id].VirtualAddress = 0;
+		nt_headers_.OptionalHeader.DataDirectory[id].Size = 0;
+
+		if(id == image_directory_entry_basereloc)
+		{
+			set_characteristics_flags(image_file_relocs_stripped);
+			set_dll_characteristics(get_dll_characteristics() & ~image_dllcharacteristics_dynamic_base);
+		}
+		else if(id == image_directory_entry_export)
+		{
+			clear_characteristics_flags(image_file_dll);
+		}
+	}
+}
+
+//Returns directory RVA
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_directory_rva(uint32_t id) const
+{
+	//Check if directory exists
+	if(nt_headers_.OptionalHeader.NumberOfRvaAndSizes <= id)
+		throw pe_exception("Specified directory does not exist", pe_exception::directory_does_not_exist);
+
+	return nt_headers_.OptionalHeader.DataDirectory[id].VirtualAddress;
+}
+
+//Returns directory size
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_directory_rva(uint32_t id, uint32_t va)
+{
+	//Check if directory exists
+	if(nt_headers_.OptionalHeader.NumberOfRvaAndSizes <= id)
+		throw pe_exception("Specified directory does not exist", pe_exception::directory_does_not_exist);
+
+	nt_headers_.OptionalHeader.DataDirectory[id].VirtualAddress = va;
+}
+
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_directory_size(uint32_t id, uint32_t size)
+{
+	//Check if directory exists
+	if(nt_headers_.OptionalHeader.NumberOfRvaAndSizes <= id)
+		throw pe_exception("Specified directory does not exist", pe_exception::directory_does_not_exist);
+
+	nt_headers_.OptionalHeader.DataDirectory[id].Size = size;
+}
+
+//Returns directory size
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_directory_size(uint32_t id) const
+{
+	//Check if directory exists
+	if(nt_headers_.OptionalHeader.NumberOfRvaAndSizes <= id)
+		throw pe_exception("Specified directory does not exist", pe_exception::directory_does_not_exist);
+
+	return nt_headers_.OptionalHeader.DataDirectory[id].Size;
+}
+
+//Strips only zero DATA_DIRECTORY entries to count = min_count
+//Returns resulting number of data directories
+//strip_iat_directory - if true, even not empty IAT directory will be stripped
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::strip_data_directories(uint32_t min_count, bool strip_iat_directory)
+{
+	int i = nt_headers_.OptionalHeader.NumberOfRvaAndSizes - 1;
+
+	//Enumerate all data directories from the end
+	for(; i >= 0; i--)
+	{
+		//If directory exists, break
+		if(nt_headers_.OptionalHeader.DataDirectory[i].VirtualAddress && (static_cast<uint32_t>(i) != image_directory_entry_iat || !strip_iat_directory))
+			break;
+
+		if(i <= static_cast<int>(min_count) - 2)
+			break;
+	}
+
+	if(i == image_numberof_directory_entries - 1)
+		return image_numberof_directory_entries;
+
+	//Return new number of data directories
+	return nt_headers_.OptionalHeader.NumberOfRvaAndSizes = i + 1;
+}
+
+//Returns image base for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_image_base_32() const
+{
+	return static_cast<uint32_t>(nt_headers_.OptionalHeader.ImageBase);
+}
+
+//Returns image base for PE32/PE64
+template<typename PEClassType>
+uint64_t pe_properties_generic<PEClassType>::get_image_base_64() const
+{
+	return static_cast<uint64_t>(nt_headers_.OptionalHeader.ImageBase);
+}
+
+//Sets new image base
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_image_base(uint32_t base)
+{
+	nt_headers_.OptionalHeader.ImageBase = base;
+}
+
+//Sets new image base
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_image_base_64(uint64_t base)
+{
+	nt_headers_.OptionalHeader.ImageBase = static_cast<typename PEClassType::BaseSize>(base);
+}
+
+//Returns image entry point
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_ep() const
+{
+	return nt_headers_.OptionalHeader.AddressOfEntryPoint;
+}
+
+//Sets image entry point
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_ep(uint32_t new_ep)
+{
+	nt_headers_.OptionalHeader.AddressOfEntryPoint = new_ep;
+}
+
+//Returns file alignment
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_file_alignment() const
+{
+	return nt_headers_.OptionalHeader.FileAlignment;
+}
+
+//Returns section alignment
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_section_alignment() const
+{
+	return nt_headers_.OptionalHeader.SectionAlignment;
+}
+
+//Sets heap size commit for PE32
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_heap_size_commit(uint32_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfHeapCommit = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets heap size commit for PE32/PE64
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_heap_size_commit(uint64_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfHeapCommit = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets heap size reserve for PE32
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_heap_size_reserve(uint32_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfHeapReserve = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets heap size reserve for PE32/PE64
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_heap_size_reserve(uint64_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfHeapReserve = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets stack size commit for PE32
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_stack_size_commit(uint32_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfStackCommit = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets stack size commit for PE32/PE64
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_stack_size_commit(uint64_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfStackCommit = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets stack size reserve for PE32
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_stack_size_reserve(uint32_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfStackReserve = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Sets stack size reserve for PE32/PE64
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_stack_size_reserve(uint64_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfStackReserve = static_cast<typename PEClassType::BaseSize>(size);
+}
+
+//Returns heap size commit for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_heap_size_commit_32() const
+{
+	return static_cast<uint32_t>(nt_headers_.OptionalHeader.SizeOfHeapCommit);
+}
+
+//Returns heap size commit for PE32/PE64
+template<typename PEClassType>
+uint64_t pe_properties_generic<PEClassType>::get_heap_size_commit_64() const
+{
+	return static_cast<uint64_t>(nt_headers_.OptionalHeader.SizeOfHeapCommit);
+}
+
+//Returns heap size reserve for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_heap_size_reserve_32() const
+{
+	return static_cast<uint32_t>(nt_headers_.OptionalHeader.SizeOfHeapReserve);
+}
+
+//Returns heap size reserve for PE32/PE64
+template<typename PEClassType>
+uint64_t pe_properties_generic<PEClassType>::get_heap_size_reserve_64() const
+{
+	return static_cast<uint64_t>(nt_headers_.OptionalHeader.SizeOfHeapReserve);
+}
+
+//Returns stack size commit for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_stack_size_commit_32() const
+{
+	return static_cast<uint32_t>(nt_headers_.OptionalHeader.SizeOfStackCommit);
+}
+
+//Returns stack size commit for PE32/PE64
+template<typename PEClassType>
+uint64_t pe_properties_generic<PEClassType>::get_stack_size_commit_64() const
+{
+	return static_cast<uint64_t>(nt_headers_.OptionalHeader.SizeOfStackCommit);
+}
+
+//Returns stack size reserve for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_stack_size_reserve_32() const
+{
+	return static_cast<uint32_t>(nt_headers_.OptionalHeader.SizeOfStackReserve);
+}
+
+//Returns stack size reserve for PE32/PE64
+template<typename PEClassType>
+uint64_t pe_properties_generic<PEClassType>::get_stack_size_reserve_64() const
+{
+	return static_cast<uint64_t>(nt_headers_.OptionalHeader.SizeOfStackReserve);
+}
+
+//Returns virtual size of image
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_size_of_image() const
+{
+	return nt_headers_.OptionalHeader.SizeOfImage;
+}
+
+//Returns number of RVA and sizes (number of DATA_DIRECTORY entries)
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_number_of_rvas_and_sizes() const
+{
+	return nt_headers_.OptionalHeader.NumberOfRvaAndSizes;
+}
+
+//Sets number of RVA and sizes (number of DATA_DIRECTORY entries)
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_number_of_rvas_and_sizes(uint32_t number)
+{
+	nt_headers_.OptionalHeader.NumberOfRvaAndSizes = number;
+}
+
+//Returns PE characteristics
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_characteristics() const
+{
+	return nt_headers_.FileHeader.Characteristics;
+}
+
+//Returns checksum of PE file from header
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_checksum() const
+{
+	return nt_headers_.OptionalHeader.CheckSum;
+}
+
+//Sets checksum of PE file
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_checksum(uint32_t checksum)
+{
+	nt_headers_.OptionalHeader.CheckSum = checksum;
+}
+
+//Returns DLL Characteristics
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_dll_characteristics() const
+{
+	return nt_headers_.OptionalHeader.DllCharacteristics;
+}
+
+//Returns timestamp of PE file from header
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_time_date_stamp() const
+{
+	return nt_headers_.FileHeader.TimeDateStamp;
+}
+
+//Sets timestamp of PE file
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_time_date_stamp(uint32_t timestamp)
+{
+	nt_headers_.FileHeader.TimeDateStamp = timestamp;
+}
+
+//Sets DLL Characteristics
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_dll_characteristics(uint16_t characteristics)
+{
+	nt_headers_.OptionalHeader.DllCharacteristics = characteristics;
+}
+
+//Returns Machine field value of PE file from header
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_machine() const
+{
+	return nt_headers_.FileHeader.Machine;
+}
+
+//Sets Machine field value of PE file
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_machine(uint16_t machine)
+{
+	nt_headers_.FileHeader.Machine = machine;
+}
+
+//Sets PE characteristics
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_characteristics(uint16_t ch)
+{
+	nt_headers_.FileHeader.Characteristics = ch;
+}
+
+//Returns size of headers
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_size_of_headers() const
+{
+	return nt_headers_.OptionalHeader.SizeOfHeaders;
+}
+
+//Returns subsystem
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_subsystem() const
+{
+	return nt_headers_.OptionalHeader.Subsystem;
+}
+
+//Sets subsystem
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_subsystem(uint16_t subsystem)
+{
+	nt_headers_.OptionalHeader.Subsystem = subsystem;
+}
+
+//Returns size of optional header
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_size_of_optional_header() const
+{
+	return nt_headers_.FileHeader.SizeOfOptionalHeader;
+}
+
+//Returns PE signature
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_pe_signature() const
+{
+	return nt_headers_.Signature;
+}
+
+//Returns PE magic value
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_magic() const
+{
+	return nt_headers_.OptionalHeader.Magic;
+}
+
+//Sets required operation system version
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_os_version(uint16_t major, uint16_t minor)
+{
+	nt_headers_.OptionalHeader.MinorOperatingSystemVersion = minor;
+	nt_headers_.OptionalHeader.MajorOperatingSystemVersion = major;
+}
+
+//Returns required operation system version (minor word)
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_minor_os_version() const
+{
+	return nt_headers_.OptionalHeader.MinorOperatingSystemVersion;
+}
+
+//Returns required operation system version (major word)
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_major_os_version() const
+{
+	return nt_headers_.OptionalHeader.MajorOperatingSystemVersion;
+}
+
+//Sets required subsystem version
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_subsystem_version(uint16_t major, uint16_t minor)
+{
+	nt_headers_.OptionalHeader.MinorSubsystemVersion = minor;
+	nt_headers_.OptionalHeader.MajorSubsystemVersion = major;
+}
+
+//Returns required subsystem version (minor word)
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_minor_subsystem_version() const
+{
+	return nt_headers_.OptionalHeader.MinorSubsystemVersion;
+}
+
+//Returns required subsystem version (major word)
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_major_subsystem_version() const
+{
+	return nt_headers_.OptionalHeader.MajorSubsystemVersion;
+}
+
+//Virtual Address (VA) to Relative Virtual Address (RVA) convertions for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::va_to_rva(uint32_t va, bool bound_check) const
+{
+	if(bound_check && static_cast<uint64_t>(va) - nt_headers_.OptionalHeader.ImageBase > pe_utils::max_dword)
+		throw pe_exception("Incorrect address conversion", pe_exception::incorrect_address_conversion);
+
+	return static_cast<uint32_t>(va - nt_headers_.OptionalHeader.ImageBase);
+}
+
+//Virtual Address (VA) to Relative Virtual Address (RVA) convertions for PE32/PE64
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::va_to_rva(uint64_t va, bool bound_check) const
+{
+	if(bound_check && va - nt_headers_.OptionalHeader.ImageBase > pe_utils::max_dword)
+		throw pe_exception("Incorrect address conversion", pe_exception::incorrect_address_conversion);
+
+	return static_cast<uint32_t>(va - nt_headers_.OptionalHeader.ImageBase);
+}
+
+//Relative Virtual Address (RVA) to Virtual Address (VA) convertions for PE32
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::rva_to_va_32(uint32_t rva) const
+{
+	if(!pe_utils::is_sum_safe(rva, static_cast<uint32_t>(nt_headers_.OptionalHeader.ImageBase)))
+		throw pe_exception("Incorrect address conversion", pe_exception::incorrect_address_conversion);
+
+	return static_cast<uint32_t>(rva + nt_headers_.OptionalHeader.ImageBase);
+}
+
+//Relative Virtual Address (RVA) to Virtual Address (VA) convertions for PE32/PE64
+template<typename PEClassType>
+uint64_t pe_properties_generic<PEClassType>::rva_to_va_64(uint32_t rva) const
+{
+	return static_cast<uint64_t>(rva) + nt_headers_.OptionalHeader.ImageBase;
+}
+
+//Returns number of sections
+template<typename PEClassType>
+uint16_t pe_properties_generic<PEClassType>::get_number_of_sections() const
+{
+	return nt_headers_.FileHeader.NumberOfSections;
+}
+
+//Sets number of sections
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_number_of_sections(uint16_t number)
+{
+	nt_headers_.FileHeader.NumberOfSections = number;
+}
+
+//Sets virtual size of image
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_size_of_image(uint32_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfImage = size;
+}
+
+//Sets size of headers
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_size_of_headers(uint32_t size)
+{
+	nt_headers_.OptionalHeader.SizeOfHeaders = size;
+}
+
+//Sets size of optional headers
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_size_of_optional_header(uint16_t size)
+{
+	nt_headers_.FileHeader.SizeOfOptionalHeader = size;
+}
+
+//Returns nt headers data pointer
+template<typename PEClassType>
+char* pe_properties_generic<PEClassType>::get_nt_headers_ptr()
+{
+	return reinterpret_cast<char*>(&nt_headers_);
+}
+
+//Returns nt headers data pointer
+template<typename PEClassType>
+const char* pe_properties_generic<PEClassType>::get_nt_headers_ptr() const
+{
+	return reinterpret_cast<const char*>(&nt_headers_);
+}
+
+//Returns size of NT header
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_sizeof_nt_header() const
+{
+	return sizeof(typename PEClassType::NtHeaders);
+}
+
+//Returns size of optional headers
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_sizeof_opt_headers() const
+{
+	return sizeof(typename PEClassType::OptHeaders);
+}
+
+//Sets file alignment (no checks)
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_file_alignment_unchecked(uint32_t alignment) 
+{
+	nt_headers_.OptionalHeader.FileAlignment = alignment;
+}
+
+//Sets base of code
+template<typename PEClassType>
+void pe_properties_generic<PEClassType>::set_base_of_code(uint32_t base)
+{
+	nt_headers_.OptionalHeader.BaseOfCode = base;
+}
+
+//Returns base of code
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_base_of_code() const
+{
+	return nt_headers_.OptionalHeader.BaseOfCode;
+}
+
+//Returns needed PE magic for PE or PE+ (from template parameters)
+template<typename PEClassType>
+uint32_t pe_properties_generic<PEClassType>::get_needed_magic() const
+{
+	return PEClassType::Id;
+}
+
+//Returns PE type of this image
+template<typename PEClassType>
+pe_type pe_properties_generic<PEClassType>::get_pe_type() const
+{
+	return PEClassType::Id == image_nt_optional_hdr32_magic ? pe_type_32 : pe_type_64;
+}
+
+//Two used instantiations for PE32 (PE) and PE64 (PE+)
+template class pe_properties_generic<pe_types_class_32>;
+template class pe_properties_generic<pe_types_class_64>;
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_properties_generic.h b/irdb-lib/pebliss/trunk/pe_lib/pe_properties_generic.h
new file mode 100644
index 0000000000000000000000000000000000000000..9a575524c397a90137d41e53de57786d92f30b13
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_properties_generic.h
@@ -0,0 +1,259 @@
+#ifndef pebliss_pe_properties_generic_h
+#define pebliss_pe_properties_generic_h
+#include "pe_properties.h"
+
+namespace pe_bliss
+{
+//Helper class to reduce code size and ease its editing
+template<
+	typename NtHeadersType,
+	typename OptHeadersType,
+	uint16_t IdVal,
+	typename BaseSizeType,
+	BaseSizeType ImportSnapFlagVal,
+	typename TLSStructType,
+	typename ConfigStructType>
+class pe_types
+{
+public:
+	typedef NtHeadersType NtHeaders; //NT HEADERS type
+	typedef OptHeadersType OptHeaders; //NT OPTIONAL HEADER type
+	typedef BaseSizeType BaseSize; //Base size of different values: DWORD or ULONGLONG
+	typedef TLSStructType TLSStruct; //TLS structure type
+	typedef ConfigStructType ConfigStruct; //Configuration structure type
+
+	static const uint16_t Id = IdVal; //Magic of PE or PE+
+	static const BaseSize ImportSnapFlag = ImportSnapFlagVal; //Import snap flag value
+};
+
+//Portable Executable derived class for PE and PE+
+//Describes PE/PE+ dependent things
+template<typename PEClassType>
+class pe_properties_generic : public pe_properties
+{
+public: //Constructor
+	virtual std::auto_ptr<pe_properties> duplicate() const;
+
+	//Fills properly PE structures
+	virtual void create_pe(uint32_t section_alignment, uint16_t subsystem);
+
+public:
+	//Destructor
+	virtual ~pe_properties_generic();
+
+
+public: //DIRECTORIES
+	//Returns true if directory exists
+	virtual bool directory_exists(uint32_t id) const;
+
+	//Removes directory
+	virtual void remove_directory(uint32_t id);
+
+	//Returns directory RVA
+	virtual uint32_t get_directory_rva(uint32_t id) const;
+	//Returns directory size
+	virtual uint32_t get_directory_size(uint32_t id) const;
+
+	//Sets directory RVA (just a value of PE header, no moving occurs)
+	virtual void set_directory_rva(uint32_t id, uint32_t rva);
+	//Sets directory size (just a value of PE header, no moving occurs)
+	virtual void set_directory_size(uint32_t id, uint32_t size);
+	
+	//Strips only zero DATA_DIRECTORY entries to count = min_count
+	//Returns resulting number of data directories
+	//strip_iat_directory - if true, even not empty IAT directory will be stripped
+	virtual uint32_t strip_data_directories(uint32_t min_count = 1, bool strip_iat_directory = true);
+
+
+public: //IMAGE
+	//Returns PE type of this image
+	virtual pe_type get_pe_type() const;
+
+
+public: //PE HEADER
+	//Returns image base for PE32 and PE64 respectively
+	virtual uint32_t get_image_base_32() const;
+	virtual uint64_t get_image_base_64() const;
+
+	//Sets new image base for PE32
+	virtual void set_image_base(uint32_t base);
+	//Sets new image base for PE32/PE+
+	virtual void set_image_base_64(uint64_t base);
+
+	//Returns image entry point
+	virtual uint32_t get_ep() const;
+	//Sets image entry point
+	virtual void set_ep(uint32_t new_ep);
+
+	//Returns file alignment
+	virtual uint32_t get_file_alignment() const;
+	//Returns section alignment
+	virtual uint32_t get_section_alignment() const;
+
+	//Sets heap size commit for PE32 and PE64 respectively
+	virtual void set_heap_size_commit(uint32_t size);
+	virtual void set_heap_size_commit(uint64_t size);
+	//Sets heap size reserve for PE32 and PE64 respectively
+	virtual void set_heap_size_reserve(uint32_t size);
+	virtual void set_heap_size_reserve(uint64_t size);
+	//Sets stack size commit for PE32 and PE64 respectively
+	virtual void set_stack_size_commit(uint32_t size);
+	virtual void set_stack_size_commit(uint64_t size);
+	//Sets stack size reserve for PE32 and PE64 respectively
+	virtual void set_stack_size_reserve(uint32_t size);
+	virtual void set_stack_size_reserve(uint64_t size);
+	
+	//Returns heap size commit for PE32 and PE64 respectively
+	virtual uint32_t get_heap_size_commit_32() const;
+	virtual uint64_t get_heap_size_commit_64() const;
+	//Returns heap size reserve for PE32 and PE64 respectively
+	virtual uint32_t get_heap_size_reserve_32() const;
+	virtual uint64_t get_heap_size_reserve_64() const;
+	//Returns stack size commit for PE32 and PE64 respectively
+	virtual uint32_t get_stack_size_commit_32() const;
+	virtual uint64_t get_stack_size_commit_64() const;
+	//Returns stack size reserve for PE32 and PE64 respectively
+	virtual uint32_t get_stack_size_reserve_32() const;
+	virtual uint64_t get_stack_size_reserve_64() const;
+
+	//Returns virtual size of image
+	virtual uint32_t get_size_of_image() const;
+
+	//Returns number of RVA and sizes (number of DATA_DIRECTORY entries)
+	virtual uint32_t get_number_of_rvas_and_sizes() const;
+	//Sets number of RVA and sizes (number of DATA_DIRECTORY entries)
+	virtual void set_number_of_rvas_and_sizes(uint32_t number);
+
+	//Returns PE characteristics
+	virtual uint16_t get_characteristics() const;
+	//Sets PE characteristics
+	virtual void set_characteristics(uint16_t ch);
+	
+	//Returns size of headers
+	virtual uint32_t get_size_of_headers() const;
+
+	//Returns subsystem
+	virtual uint16_t get_subsystem() const;
+
+	//Sets subsystem
+	virtual void set_subsystem(uint16_t subsystem);
+
+	//Returns size of optional header
+	virtual uint16_t get_size_of_optional_header() const;
+
+	//Returns PE signature
+	virtual uint32_t get_pe_signature() const;
+
+	//Returns PE magic value
+	virtual uint32_t get_magic() const;
+
+	//Returns checksum of PE file from header
+	virtual uint32_t get_checksum() const;
+	
+	//Sets checksum of PE file
+	virtual void set_checksum(uint32_t checksum);
+	
+	//Returns timestamp of PE file from header
+	virtual uint32_t get_time_date_stamp() const;
+	
+	//Sets timestamp of PE file
+	virtual void set_time_date_stamp(uint32_t timestamp);
+	
+	//Returns Machine field value of PE file from header
+	virtual uint16_t get_machine() const;
+
+	//Sets Machine field value of PE file
+	virtual void set_machine(uint16_t machine);
+
+	//Returns DLL Characteristics
+	virtual uint16_t get_dll_characteristics() const;
+	
+	//Sets DLL Characteristics
+	virtual void set_dll_characteristics(uint16_t characteristics);
+	
+	//Sets required operation system version
+	virtual void set_os_version(uint16_t major, uint16_t minor);
+
+	//Returns required operation system version (minor word)
+	virtual uint16_t get_minor_os_version() const;
+
+	//Returns required operation system version (major word)
+	virtual uint16_t get_major_os_version() const;
+
+	//Sets required subsystem version
+	virtual void set_subsystem_version(uint16_t major, uint16_t minor);
+
+	//Returns required subsystem version (minor word)
+	virtual uint16_t get_minor_subsystem_version() const;
+
+	//Returns required subsystem version (major word)
+	virtual uint16_t get_major_subsystem_version() const;
+
+public: //ADDRESS CONVERTIONS
+	//Virtual Address (VA) to Relative Virtual Address (RVA) convertions
+	//for PE32 and PE64 respectively
+	//bound_check checks integer overflow
+	virtual uint32_t va_to_rva(uint32_t va, bool bound_check = true) const;
+	virtual uint32_t va_to_rva(uint64_t va, bool bound_check = true) const;
+	
+	//Relative Virtual Address (RVA) to Virtual Address (VA) convertions
+	//for PE32 and PE64 respectively
+	virtual uint32_t rva_to_va_32(uint32_t rva) const;
+	virtual uint64_t rva_to_va_64(uint32_t rva) const;
+
+
+public: //SECTIONS
+	//Returns number of sections
+	virtual uint16_t get_number_of_sections() const;
+
+protected:
+	typename PEClassType::NtHeaders nt_headers_; //NT headers (PE32 or PE64)
+	
+public:
+	//Sets number of sections
+	virtual void set_number_of_sections(uint16_t number);
+	//Sets virtual size of image
+	virtual void set_size_of_image(uint32_t size);
+	//Sets size of headers
+	virtual void set_size_of_headers(uint32_t size);
+	//Sets size of optional headers
+	virtual void set_size_of_optional_header(uint16_t size);
+	//Returns nt headers data pointer
+	virtual char* get_nt_headers_ptr();
+	//Returns nt headers data pointer
+	virtual const char* get_nt_headers_ptr() const;
+	//Returns size of NT header
+	virtual uint32_t get_sizeof_nt_header() const;
+	//Returns size of optional headers
+	virtual uint32_t get_sizeof_opt_headers() const;
+	//Sets file alignment (no checks)
+	virtual void set_file_alignment_unchecked(uint32_t alignment);
+	//Sets base of code
+	virtual void set_base_of_code(uint32_t base);
+	//Returns base of code
+	virtual uint32_t get_base_of_code() const;
+	//Returns needed PE magic for PE or PE+ (from template parameters)
+	virtual uint32_t get_needed_magic() const;
+};
+
+//Two used typedefs for PE32 (PE) and PE64 (PE+)
+typedef pe_types<pe_win::image_nt_headers32,
+	pe_win::image_optional_header32,
+	pe_win::image_nt_optional_hdr32_magic,
+	uint32_t,
+	pe_win::image_ordinal_flag32,
+	pe_win::image_tls_directory32,
+	pe_win::image_load_config_directory32> pe_types_class_32;
+
+typedef pe_types<pe_win::image_nt_headers64,
+	pe_win::image_optional_header64,
+	pe_win::image_nt_optional_hdr64_magic,
+	uint64_t,
+	pe_win::image_ordinal_flag64,
+	pe_win::image_tls_directory64,
+	pe_win::image_load_config_directory64> pe_types_class_64;
+
+typedef pe_properties_generic<pe_types_class_32> pe_properties_32;
+typedef pe_properties_generic<pe_types_class_64> pe_properties_64;
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_rebuilder.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_rebuilder.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..4cc6faf14ac5ac6fb123de12740d4311a3fa9724
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_rebuilder.cpp
@@ -0,0 +1,177 @@
+#include "pe_rebuilder.h"
+#include "pe_base.h"
+#include "pe_structures.h"
+#include "pe_exception.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Rebuilds PE image headers
+//If strip_dos_header is true, DOS headers partially will be used for PE headers
+//If change_size_of_headers == true, SizeOfHeaders will be recalculated automatically
+//If save_bound_import == true, existing bound import directory will be saved correctly (because some compilers and bind.exe put it to PE headers)
+void rebuild_pe(pe_base& pe, image_dos_header& dos_header, bool strip_dos_header, bool change_size_of_headers, bool save_bound_import)
+{
+	dos_header = pe.get_dos_header();
+
+	if(strip_dos_header)
+	{
+		//Strip stub overlay
+		pe.strip_stub_overlay();
+		//BaseOfCode NT Headers field now overlaps
+		//e_lfanew field, so we're acrually setting
+		//e_lfanew with this call
+		pe.set_base_of_code(8 * sizeof(uint16_t));
+	}
+	else
+	{
+		//Set start of PE headers
+		dos_header.e_lfanew = sizeof(image_dos_header)
+			+ pe_utils::align_up(static_cast<uint32_t>(pe.get_stub_overlay().size()), sizeof(uint32_t));
+	}
+
+	section_list& sections = pe.get_image_sections();
+
+	//Calculate pointer to section data
+	size_t ptr_to_section_data = (strip_dos_header ? 8 * sizeof(uint16_t) : sizeof(image_dos_header)) + pe.get_sizeof_nt_header()
+		+ pe_utils::align_up(pe.get_stub_overlay().size(), sizeof(uint32_t))
+		- sizeof(image_data_directory) * (image_numberof_directory_entries - pe.get_number_of_rvas_and_sizes())
+		+ sections.size() * sizeof(image_section_header);
+
+	if(save_bound_import && pe.has_bound_import())
+	{
+		//It will be aligned to DWORD, because we're aligning to DWORD everything above it
+		pe.set_directory_rva(image_directory_entry_bound_import, static_cast<uint32_t>(ptr_to_section_data));
+		ptr_to_section_data += pe.get_directory_size(image_directory_entry_bound_import);	
+	}
+	
+	ptr_to_section_data = pe_utils::align_up(ptr_to_section_data, pe.get_file_alignment());
+
+	//Set size of headers and size of optional header
+	if(change_size_of_headers)
+	{
+		if(!pe.get_image_sections().empty())
+		{
+			if(static_cast<uint32_t>(ptr_to_section_data) > (*sections.begin()).get_virtual_address())
+				throw pe_exception("Headers of PE file are too long. Try to strip STUB or don't build bound import", pe_exception::cannot_rebuild_image);
+		}
+
+		pe.set_size_of_headers(static_cast<uint32_t>(ptr_to_section_data));
+	}
+
+	//Set number of sections in PE header
+	pe.update_number_of_sections();
+
+	pe.update_image_size();
+
+	pe.set_size_of_optional_header(static_cast<uint16_t>(pe.get_sizeof_opt_headers()
+		- sizeof(image_data_directory) * (image_numberof_directory_entries - pe.get_number_of_rvas_and_sizes())));
+
+	//Recalculate pointer to raw data according to section list
+	for(section_list::iterator it = sections.begin(); it != sections.end(); ++it)
+	{
+		//Save section headers PointerToRawData
+		(*it).set_pointer_to_raw_data(static_cast<uint32_t>(ptr_to_section_data));
+		ptr_to_section_data += (*it).get_aligned_raw_size(pe.get_file_alignment());
+	}
+}
+
+//Rebuild PE image and write it to "out" ostream
+//If strip_dos_header is true, DOS headers partially will be used for PE headers
+//If change_size_of_headers == true, SizeOfHeaders will be recalculated automatically
+//If save_bound_import == true, existing bound import directory will be saved correctly (because some compilers and bind.exe put it to PE headers)
+void rebuild_pe(pe_base& pe, std::ostream& out, bool strip_dos_header, bool change_size_of_headers, bool save_bound_import)
+{
+	if(out.bad())
+		throw pe_exception("Stream is bad", pe_exception::stream_is_bad);
+
+	if(save_bound_import && pe.has_bound_import())
+	{
+		if(pe.section_data_length_from_rva(pe.get_directory_rva(image_directory_entry_bound_import), pe.get_directory_rva(image_directory_entry_bound_import), section_data_raw, true)
+			< pe.get_directory_size(image_directory_entry_bound_import))
+			throw pe_exception("Incorrect bound import directory", pe_exception::incorrect_bound_import_directory);
+	}
+
+	//Change ostream state
+	out.exceptions(std::ios::goodbit);
+	out.clear();
+	
+	uint32_t original_bound_import_rva = pe.has_bound_import() ? pe.get_directory_rva(image_directory_entry_bound_import) : 0;
+	if(original_bound_import_rva && original_bound_import_rva > pe.get_size_of_headers())
+	{
+		//No need to do anything with bound import directory
+		//if it is placed inside of any section, not headers
+		original_bound_import_rva = 0;
+		save_bound_import = false;
+	}
+
+	{
+		image_dos_header dos_header;
+
+		//Rebuild PE image headers
+		rebuild_pe(pe, dos_header, strip_dos_header, change_size_of_headers, save_bound_import);
+
+		//Write DOS header
+		out.write(reinterpret_cast<const char*>(&dos_header), strip_dos_header ? 8 * sizeof(uint16_t) : sizeof(image_dos_header));
+	}
+
+	//If we have stub overlay, write it too
+	{
+		const std::string& stub = pe.get_stub_overlay();
+		if(stub.size())
+		{
+			out.write(stub.data(), stub.size());
+			size_t aligned_size = pe_utils::align_up(stub.size(), sizeof(uint32_t));
+			//Align PE header, which is right after rich overlay
+			while(aligned_size > stub.size())
+			{
+				out.put('\0');
+				--aligned_size;
+			}
+		}
+	}
+	
+	//Write NT headers
+	out.write(static_cast<const pe_base&>(pe).get_nt_headers_ptr(), pe.get_sizeof_nt_header()
+		- sizeof(image_data_directory) * (image_numberof_directory_entries - pe.get_number_of_rvas_and_sizes()));
+
+	//Write section headers
+	const section_list& sections = pe.get_image_sections();
+	for(section_list::const_iterator it = sections.begin(); it != sections.end(); ++it)
+	{
+		if(it == sections.end() - 1) //If last section encountered
+		{
+			image_section_header header((*it).get_raw_header());
+			header.SizeOfRawData = static_cast<uint32_t>((*it).get_raw_data().length()); //Set non-aligned actual data length for it
+			out.write(reinterpret_cast<const char*>(&header), sizeof(image_section_header));
+		}
+		else
+		{
+			out.write(reinterpret_cast<const char*>(&(*it).get_raw_header()), sizeof(image_section_header));
+		}
+	}
+
+	//Write bound import data if requested
+	if(save_bound_import && pe.has_bound_import())
+	{
+		out.write(pe.section_data_from_rva(original_bound_import_rva, section_data_raw, true),
+			pe.get_directory_size(image_directory_entry_bound_import));
+	}
+
+	//Write section data finally
+	for(section_list::const_iterator it = sections.begin(); it != sections.end(); ++it)
+	{
+		const section& s = *it;
+
+		std::streamoff wpos = out.tellp();
+
+		//Fill unused overlay data between sections with null bytes
+		for(unsigned int i = 0; i < s.get_pointer_to_raw_data() - wpos; i++)
+			out.put(0);
+
+		//Write raw section data
+		out.write(s.get_raw_data().data(), s.get_raw_data().length());
+	}
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_rebuilder.h b/irdb-lib/pebliss/trunk/pe_lib/pe_rebuilder.h
new file mode 100644
index 0000000000000000000000000000000000000000..ad9d7cc6fa736652336243d062d86522fa014819
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_rebuilder.h
@@ -0,0 +1,14 @@
+#ifndef pebliss_pe_rebuilder_h
+#define pebliss_pe_rebuilder_h
+#pragma once
+#include <ostream>
+
+namespace pe_bliss
+{
+class pe_base;
+//Rebuilds PE image, writes resulting image to ostream "out". If strip_dos_header == true, DOS header will be stripped a little
+//If change_size_of_headers == true, SizeOfHeaders will be recalculated automatically
+//If save_bound_import == true, existing bound import directory will be saved correctly (because some compilers and bind.exe put it to PE headers)
+void rebuild_pe(pe_base& pe, std::ostream& out, bool strip_dos_header = false, bool change_size_of_headers = true, bool save_bound_import = true);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_relocations.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_relocations.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..2d674e1346f1d946bff887fcda2b3b687827e5e3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_relocations.cpp
@@ -0,0 +1,299 @@
+#include <string.h>
+#include "pe_relocations.h"
+#include "pe_properties_generic.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//RELOCATIONS
+//Default constructor
+relocation_entry::relocation_entry()
+	:rva_(0), type_(0)
+{}
+
+//Constructor from relocation item (WORD)
+relocation_entry::relocation_entry(uint16_t relocation_value)
+	:rva_(relocation_value & ((1 << 12) - 1)), type_(relocation_value >> 12)
+{}
+
+//Constructor from relative rva and relocation type
+relocation_entry::relocation_entry(uint16_t rrva, uint16_t type)
+	:rva_(rrva), type_(type)
+{}
+
+//Returns RVA of relocation
+uint16_t relocation_entry::get_rva() const
+{
+	return rva_;
+}
+
+//Returns type of relocation
+uint16_t relocation_entry::get_type() const
+{
+	return type_;
+}
+
+//Sets RVA of relocation
+void relocation_entry::set_rva(uint16_t rva)
+{
+	rva_ = rva;
+}
+
+//Sets type of relocation
+void relocation_entry::set_type(uint16_t type)
+{
+	type_ = type;
+}
+
+//Returns relocation item (rrva + type)
+uint16_t relocation_entry::get_item() const
+{
+	return rva_ | (type_ << 12);
+}
+
+//Sets relocation item (rrva + type)
+void relocation_entry::set_item(uint16_t item)
+{
+	rva_ = item & ((1 << 12) - 1);
+	type_ = item >> 12;
+}
+
+//Returns relocation list
+const relocation_table::relocation_list& relocation_table::get_relocations() const
+{
+	return relocations_;
+}
+
+//Adds relocation to table
+void relocation_table::add_relocation(const relocation_entry& entry)
+{
+	relocations_.push_back(entry);
+}
+
+//Default constructor
+relocation_table::relocation_table()
+	:rva_(0)
+{}
+
+//Constructor from RVA of relocation table
+relocation_table::relocation_table(uint32_t rva)
+	:rva_(rva)
+{}
+
+//Returns RVA of block
+uint32_t relocation_table::get_rva() const
+{
+	return rva_;
+}
+
+//Sets RVA of block
+void relocation_table::set_rva(uint32_t rva)
+{
+	rva_ = rva;
+}
+
+//Returns changeable relocation list
+relocation_table::relocation_list& relocation_table::get_relocations()
+{
+	return relocations_;
+}
+
+//Get relocation list of pe file, supports one-word sized relocations only
+//If list_absolute_entries = true, IMAGE_REL_BASED_ABSOLUTE will be listed
+const relocation_table_list get_relocations(const pe_base& pe, bool list_absolute_entries)
+{
+	relocation_table_list ret;
+
+	//If image does not have relocations
+	if(!pe.has_reloc())
+		return ret;
+
+	//Check the length in bytes of the section containing relocation directory
+	if(pe.section_data_length_from_rva(pe.get_directory_rva(image_directory_entry_basereloc),
+		pe.get_directory_rva(image_directory_entry_basereloc), section_data_virtual, true)
+		< sizeof(image_base_relocation))
+		throw pe_exception("Incorrect relocation directory", pe_exception::incorrect_relocation_directory);
+
+	unsigned long current_pos = pe.get_directory_rva(image_directory_entry_basereloc);
+	//First IMAGE_BASE_RELOCATION table
+	image_base_relocation reloc_table = pe.section_data_from_rva<image_base_relocation>(current_pos, section_data_virtual, true);
+
+	if(reloc_table.SizeOfBlock % 2)
+		throw pe_exception("Incorrect relocation directory", pe_exception::incorrect_relocation_directory);
+
+	unsigned long reloc_size = pe.get_directory_size(image_directory_entry_basereloc);
+	unsigned long read_size = 0;
+
+	//reloc_table.VirtualAddress is not checked (not so important)
+	while(reloc_table.SizeOfBlock && read_size < reloc_size)
+	{
+		//Create relocation table
+		relocation_table table;
+		//Save RVA
+		table.set_rva(reloc_table.VirtualAddress);
+
+		if(!pe_utils::is_sum_safe(current_pos, reloc_table.SizeOfBlock))
+			throw pe_exception("Incorrect relocation directory", pe_exception::incorrect_relocation_directory);
+
+		//List all relocations
+		for(unsigned long i = sizeof(image_base_relocation); i < reloc_table.SizeOfBlock; i += sizeof(uint16_t))
+		{
+			relocation_entry entry(pe.section_data_from_rva<uint16_t>(current_pos + i, section_data_virtual, true));
+			if(list_absolute_entries || entry.get_type() != image_rel_based_absolute)
+				table.add_relocation(entry);
+		}
+
+		//Save table
+		ret.push_back(table);
+		
+		//Go to next relocation block
+		if(!pe_utils::is_sum_safe(current_pos, reloc_table.SizeOfBlock))
+			throw pe_exception("Incorrect relocation directory", pe_exception::incorrect_relocation_directory);
+
+		current_pos += reloc_table.SizeOfBlock;
+		read_size += reloc_table.SizeOfBlock;
+		reloc_table = pe.section_data_from_rva<image_base_relocation>(current_pos, section_data_virtual, true);
+	}
+
+	return ret;
+}
+
+//Simple relocations rebuilder
+//To keep PE file working, don't remove any of existing relocations in
+//relocation_table_list returned by a call to get_relocations() function
+//auto_strip_last_section - if true and relocations are placed in the last section, it will be automatically stripped
+//offset_from_section_start - offset from the beginning of reloc_section, where relocations data will be situated
+//If save_to_pe_header is true, PE header will be modified automatically
+const image_directory rebuild_relocations(pe_base& pe, const relocation_table_list& relocs, section& reloc_section, uint32_t offset_from_section_start, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	//Check that reloc_section is attached to this PE image
+	if(!pe.section_attached(reloc_section))
+		throw pe_exception("Relocations section must be attached to PE file", pe_exception::section_is_not_attached);
+	
+	uint32_t current_reloc_data_pos = pe_utils::align_up(offset_from_section_start, sizeof(uint32_t));
+
+	uint32_t needed_size = current_reloc_data_pos - offset_from_section_start; //Calculate needed size for relocation tables
+	uint32_t size_delta = needed_size;
+
+	uint32_t start_reloc_pos = current_reloc_data_pos;
+
+	//Enumerate relocation tables
+	for(relocation_table_list::const_iterator it = relocs.begin(); it != relocs.end(); ++it)
+	{
+		needed_size += static_cast<uint32_t>((*it).get_relocations().size() * sizeof(uint16_t) /* relocations */ + sizeof(image_base_relocation) /* table header */);
+		//End of each table will be DWORD-aligned
+		if((start_reloc_pos + needed_size - size_delta) % sizeof(uint32_t))
+			needed_size += sizeof(uint16_t); //Align it with IMAGE_REL_BASED_ABSOLUTE relocation
+	}
+
+	//Check if reloc_section is last one. If it's not, check if there's enough place for relocations data
+	if(&reloc_section != &*(pe.get_image_sections().end() - 1) && 
+		(reloc_section.empty() || pe_utils::align_up(reloc_section.get_size_of_raw_data(), pe.get_file_alignment()) < needed_size + current_reloc_data_pos))
+		throw pe_exception("Insufficient space for relocations directory", pe_exception::insufficient_space);
+
+	std::string& raw_data = reloc_section.get_raw_data();
+
+	//This will be done only if reloc_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + current_reloc_data_pos)
+		raw_data.resize(needed_size + current_reloc_data_pos); //Expand section raw data
+
+	//Enumerate relocation tables
+	for(relocation_table_list::const_iterator it = relocs.begin(); it != relocs.end(); ++it)
+	{
+		//Create relocation table header
+		image_base_relocation reloc;
+		reloc.VirtualAddress = (*it).get_rva();
+		const relocation_table::relocation_list& reloc_list = (*it).get_relocations();
+		reloc.SizeOfBlock = static_cast<uint32_t>(sizeof(image_base_relocation) + sizeof(uint16_t) * reloc_list.size());
+		if((reloc_list.size() * sizeof(uint16_t)) % sizeof(uint32_t)) //If we must align end of relocation table
+			reloc.SizeOfBlock += sizeof(uint16_t);
+
+		memcpy(&raw_data[current_reloc_data_pos], &reloc, sizeof(reloc));
+		current_reloc_data_pos += sizeof(reloc);
+
+		//Enumerate relocations in table
+		for(relocation_table::relocation_list::const_iterator r = reloc_list.begin(); r != reloc_list.end(); ++r)
+		{
+			//Save relocations
+			uint16_t reloc_value = (*r).get_item();
+			memcpy(&raw_data[current_reloc_data_pos], &reloc_value, sizeof(reloc_value));
+			current_reloc_data_pos += sizeof(reloc_value);
+		}
+
+		if(current_reloc_data_pos % sizeof(uint32_t)) //If end of table is not DWORD-aligned
+		{
+			memset(&raw_data[current_reloc_data_pos], 0, sizeof(uint16_t)); //Align it with IMAGE_REL_BASED_ABSOLUTE relocation
+			current_reloc_data_pos += sizeof(uint16_t);
+		}
+	}
+
+	image_directory ret(pe.rva_from_section_offset(reloc_section, start_reloc_pos), needed_size - size_delta);
+	
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(reloc_section, auto_strip_last_section);
+
+	//If auto-rewrite of PE headers is required
+	if(save_to_pe_header)
+	{
+		pe.set_directory_rva(image_directory_entry_basereloc, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_basereloc, ret.get_size());
+
+		pe.clear_characteristics_flags(image_file_relocs_stripped);
+		pe.set_dll_characteristics(pe.get_dll_characteristics() | image_dllcharacteristics_dynamic_base);
+	}
+
+	return ret;
+}
+
+//Recalculates image base with the help of relocation tables
+void rebase_image(pe_base& pe, const relocation_table_list& tables, uint64_t new_base)
+{
+	pe.get_pe_type() == pe_type_32
+		? rebase_image_base<pe_types_class_32>(pe, tables, new_base)
+		: rebase_image_base<pe_types_class_64>(pe, tables, new_base);
+}
+
+//RELOCATIONS
+//Recalculates image base with the help of relocation tables
+//Recalculates VAs of DWORDS/QWORDS in image according to relocations
+//Notice: if you move some critical structures like TLS, image relocations will not fix new
+//positions of TLS VAs. Instead, some bytes that now doesn't belong to TLS will be fixed.
+//It is recommended to rebase image in the very beginning and move all structures afterwards.
+template<typename PEClassType>
+void rebase_image_base(pe_base& pe, const relocation_table_list& tables, uint64_t new_base)
+{
+	//Get current image base value
+	typename PEClassType::BaseSize image_base;
+	pe.get_image_base(image_base);
+
+	//ImageBase difference
+	typename PEClassType::BaseSize base_rel = static_cast<typename PEClassType::BaseSize>(static_cast<int64_t>(new_base) - image_base);
+
+	//We need to fix addresses from relocation tables
+	//Enumerate relocation tables
+	for(relocation_table_list::const_iterator it = tables.begin(); it != tables.end(); ++it)
+	{
+		const relocation_table::relocation_list& relocs = (*it).get_relocations();
+
+		uint32_t base_rva = (*it).get_rva();
+
+		//Enumerate relocations
+		for(relocation_table::relocation_list::const_iterator rel = relocs.begin(); rel != relocs.end(); ++rel)
+		{
+			//Skip ABSOLUTE entries
+			if((*rel).get_type() == pe_win::image_rel_based_absolute)
+				continue;
+			
+			//Recalculate value by RVA and rewrite it
+			uint32_t current_rva = base_rva + (*rel).get_rva();
+			typename PEClassType::BaseSize value = pe.section_data_from_rva<typename PEClassType::BaseSize>(current_rva, section_data_raw, true);
+			value += base_rel;
+			memcpy(pe.section_data_from_rva(current_rva, true), &value, sizeof(value));
+		}
+	}
+
+	//Finally, save new image base
+	pe.set_image_base_64(new_base);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_relocations.h b/irdb-lib/pebliss/trunk/pe_lib/pe_relocations.h
new file mode 100644
index 0000000000000000000000000000000000000000..313dafb65d57397bf93501c14d9bbed8ebff7cf4
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_relocations.h
@@ -0,0 +1,104 @@
+#ifndef pebliss_pe_relocations_h
+#define pebliss_pe_relocations_h
+#pragma once
+#include <vector>
+#include "pe_structures.h"
+#include "pe_base.h"
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Class representing relocation entry
+//RVA of relocation is not actually RVA, but
+//(real RVA) - (RVA of table)
+class relocation_entry
+{
+public:
+	//Default constructor
+	relocation_entry();
+	//Constructor from relocation item (WORD)
+	explicit relocation_entry(uint16_t relocation_value);
+	//Constructor from relative rva and relocation type
+	relocation_entry(uint16_t rrva, uint16_t type);
+
+	//Returns RVA of relocation (actually, relative RVA from relocation table RVA)
+	uint16_t get_rva() const;
+	//Returns type of relocation
+	uint16_t get_type() const;
+
+	//Returns relocation item (rrva + type)
+	uint16_t get_item() const;
+
+public: //Setters do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild relocations using rebuild_relocations()
+
+	//Sets RVA of relocation (actually, relative RVA from relocation table RVA)
+	void set_rva(uint16_t rva);
+	//Sets type of relocation
+	void set_type(uint16_t type);
+		
+	//Sets relocation item (rrva + type)
+	void set_item(uint16_t item);
+
+private:
+	uint16_t rva_;
+	uint16_t type_;
+};
+
+//Class representing relocation table
+class relocation_table
+{
+public:
+	typedef std::vector<relocation_entry> relocation_list;
+
+public:
+	//Default constructor
+	relocation_table();
+	//Constructor from RVA of relocation table
+	explicit relocation_table(uint32_t rva);
+
+	//Returns relocation list
+	const relocation_list& get_relocations() const;
+	//Returns RVA of block
+	uint32_t get_rva() const;
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild relocations using rebuild_relocations()
+
+	//Adds relocation to table
+	void add_relocation(const relocation_entry& entry);
+	//Returns changeable relocation list
+	relocation_list& get_relocations();
+	//Sets RVA of block
+	void set_rva(uint32_t rva);
+
+private:
+	uint32_t rva_;
+	relocation_list relocations_;
+};
+
+typedef std::vector<relocation_table> relocation_table_list;
+
+//Get relocation list of pe file, supports one-word sized relocations only
+//If list_absolute_entries = true, IMAGE_REL_BASED_ABSOLUTE will be listed
+const relocation_table_list get_relocations(const pe_base& pe, bool list_absolute_entries = false);
+
+//Simple relocations rebuilder
+//To keep PE file working, don't remove any of existing relocations in
+//relocation_table_list returned by a call to get_relocations() function
+//auto_strip_last_section - if true and relocations are placed in the last section, it will be automatically stripped
+//offset_from_section_start - offset from the beginning of reloc_section, where relocations data will be situated
+//If save_to_pe_header is true, PE header will be modified automatically
+const image_directory rebuild_relocations(pe_base& pe, const relocation_table_list& relocs, section& reloc_section, uint32_t offset_from_section_start = 0, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+
+//Recalculates image base with the help of relocation tables
+//Recalculates VAs of DWORDS/QWORDS in image according to relocations
+//Notice: if you move some critical structures like TLS, image relocations will not fix new
+//positions of TLS VAs. Instead, some bytes that now doesn't belong to TLS will be fixed.
+//It is recommended to rebase image in the very beginning and move all structures afterwards.
+void rebase_image(pe_base& pe, const relocation_table_list& tables, uint64_t new_base);
+
+template<typename PEClassType>
+void rebase_image_base(pe_base& pe, const relocation_table_list& tables, uint64_t new_base);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_resource_manager.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_manager.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1db952efcb5e7dce69c5672c40719a4b481b63fb
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_manager.cpp
@@ -0,0 +1,265 @@
+#include <algorithm>
+#include <sstream>
+#include <iomanip>
+#include <math.h>
+#include <string.h>
+#include "pe_resource_manager.h"
+#include "resource_internal.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Constructor from root resource directory
+pe_resource_manager::pe_resource_manager(resource_directory& root_directory)
+	:pe_resource_viewer(root_directory), root_dir_edit_(root_directory)
+{}
+
+resource_directory& pe_resource_manager::get_root_directory()
+{
+	return root_dir_edit_;
+}
+
+//Removes all resources of given type or root name
+//If there's more than one directory entry of a given type, only the
+//first one will be deleted (that's an unusual situation)
+//Returns true if resource was deleted
+bool pe_resource_manager::remove_resource_type(resource_type type)
+{
+	//Search for resource type
+	resource_directory::entry_list& entries = root_dir_edit_.get_entry_list();
+	resource_directory::entry_list::iterator it = std::find_if(entries.begin(), entries.end(), resource_directory::id_entry_finder(type));
+	if(it != entries.end())
+	{
+		//Remove it, if found
+		entries.erase(it);
+		return true;
+	}
+
+	return false;
+}
+
+bool pe_resource_manager::remove_resource(const std::wstring& root_name)
+{
+	//Search for resource type
+	resource_directory::entry_list& entries = root_dir_edit_.get_entry_list();
+	resource_directory::entry_list::iterator it = std::find_if(entries.begin(), entries.end(), resource_directory::name_entry_finder(root_name));
+	if(it != entries.end())
+	{
+		//Remove it, if found
+		entries.erase(it);
+		return true;
+	}
+
+	return false;
+}
+
+//Helper to remove resource
+bool pe_resource_manager::remove_resource(const resource_directory::entry_finder& root_finder, const resource_directory::entry_finder& finder)
+{
+	//Search for resource type
+	resource_directory::entry_list& entries_type = root_dir_edit_.get_entry_list();
+	resource_directory::entry_list::iterator it_type = std::find_if(entries_type.begin(), entries_type.end(), root_finder);
+	if(it_type != entries_type.end())
+	{
+		//Search for resource name/ID with "finder"
+		resource_directory::entry_list& entries_name = (*it_type).get_resource_directory().get_entry_list();
+		resource_directory::entry_list::iterator it_name = std::find_if(entries_name.begin(), entries_name.end(), finder);
+		if(it_name != entries_name.end())
+		{
+			//Erase resource, if found
+			entries_name.erase(it_name);
+			if(entries_name.empty())
+				entries_type.erase(it_type);
+
+			return true;
+		}
+	}
+
+	return false;
+}
+
+//Removes all resource languages by resource type/root name and name
+//Deletes only one entry of given type and name
+//Returns true if resource was deleted
+bool pe_resource_manager::remove_resource(resource_type type, const std::wstring& name)
+{
+	return remove_resource(resource_directory::entry_finder(type), resource_directory::entry_finder(name));
+}
+
+bool pe_resource_manager::remove_resource(const std::wstring& root_name, const std::wstring& name)
+{
+	return remove_resource(resource_directory::entry_finder(root_name), resource_directory::entry_finder(name));
+}
+
+//Removes all resource languages by resource type/root name and ID
+//Deletes only one entry of given type and ID
+//Returns true if resource was deleted
+bool pe_resource_manager::remove_resource(resource_type type, uint32_t id)
+{
+	return remove_resource(resource_directory::entry_finder(type), resource_directory::entry_finder(id));
+}
+
+bool pe_resource_manager::remove_resource(const std::wstring& root_name, uint32_t id)
+{
+	return remove_resource(resource_directory::entry_finder(root_name), resource_directory::entry_finder(id));
+}
+
+//Helper to remove resource
+bool pe_resource_manager::remove_resource(const resource_directory::entry_finder& root_finder, const resource_directory::entry_finder& finder, uint32_t language)
+{
+	//Search for resource type
+	resource_directory::entry_list& entries_type = root_dir_edit_.get_entry_list();
+	resource_directory::entry_list::iterator it_type = std::find_if(entries_type.begin(), entries_type.end(), root_finder);
+	if(it_type != entries_type.end())
+	{
+		//Search for resource name/ID with "finder"
+		resource_directory::entry_list& entries_name = (*it_type).get_resource_directory().get_entry_list();
+		resource_directory::entry_list::iterator it_name = std::find_if(entries_name.begin(), entries_name.end(), finder);
+		if(it_name != entries_name.end())
+		{
+			//Search for resource language
+			resource_directory::entry_list& entries_lang = (*it_name).get_resource_directory().get_entry_list();
+			resource_directory::entry_list::iterator it_lang = std::find_if(entries_lang.begin(), entries_lang.end(), resource_directory::id_entry_finder(language));
+			if(it_lang != entries_lang.end())
+			{
+				//Erase resource, if found
+				entries_lang.erase(it_lang);
+				if(entries_lang.empty())
+				{
+					entries_name.erase(it_name);
+					if(entries_name.empty())
+						entries_type.erase(it_type);
+				}
+
+				return true;
+			}
+		}
+	}
+
+	return false;
+}
+
+//Removes resource language by resource type/root name and name
+//Deletes only one entry of given type, name and language
+//Returns true if resource was deleted
+bool pe_resource_manager::remove_resource(resource_type type, const std::wstring& name, uint32_t language)
+{
+	return remove_resource(resource_directory::entry_finder(type), resource_directory::entry_finder(name), language);
+}
+
+bool pe_resource_manager::remove_resource(const std::wstring& root_name, const std::wstring& name, uint32_t language)
+{
+	return remove_resource(resource_directory::entry_finder(root_name), resource_directory::entry_finder(name), language);
+}
+
+//Removes recource language by resource type/root name and ID
+//Deletes only one entry of given type, ID and language
+//Returns true if resource was deleted
+bool pe_resource_manager::remove_resource(resource_type type, uint32_t id, uint32_t language)
+{
+	return remove_resource(resource_directory::entry_finder(type), resource_directory::entry_finder(id), language);
+}
+
+bool pe_resource_manager::remove_resource(const std::wstring& root_name, uint32_t id, uint32_t language)
+{
+	return remove_resource(resource_directory::entry_finder(root_name), resource_directory::entry_finder(id), language);
+}
+
+//Helper to add/replace resource
+void pe_resource_manager::add_resource(const std::string& data, resource_type type, resource_directory_entry& new_entry, const resource_directory::entry_finder& finder, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_type_entry;
+	new_type_entry.set_id(type);
+
+	add_resource(data, new_type_entry, resource_directory::entry_finder(type), new_entry, finder, language, codepage, timestamp);
+}
+
+//Helper to add/replace resource
+void pe_resource_manager::add_resource(const std::string& data, const std::wstring& root_name, resource_directory_entry& new_entry, const resource_directory::entry_finder& finder, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_type_entry;
+	new_type_entry.set_name(root_name);
+	
+	add_resource(data, new_type_entry, resource_directory::entry_finder(root_name), new_entry, finder, language, codepage, timestamp);
+}
+
+//Helper to add/replace resource
+void pe_resource_manager::add_resource(const std::string& data, resource_directory_entry& new_root_entry, const resource_directory::entry_finder& root_finder, resource_directory_entry& new_entry, const resource_directory::entry_finder& finder, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	//Search for resource type
+	resource_directory::entry_list* entries = &root_dir_edit_.get_entry_list();
+	resource_directory::entry_list::iterator it = std::find_if(entries->begin(), entries->end(), root_finder);
+	if(it == entries->end())
+	{
+		//Add resource type directory, if it was not found
+		resource_directory dir;
+		dir.set_timestamp(timestamp);
+		new_root_entry.add_resource_directory(dir);
+		entries->push_back(new_root_entry);
+		it = entries->end() - 1;
+	}
+
+	//Search for resource name/ID directory with "finder"
+	entries = &(*it).get_resource_directory().get_entry_list();
+	it = std::find_if(entries->begin(), entries->end(), finder);
+	if(it == entries->end())
+	{
+		//Add resource name/ID directory, if it was not found
+		resource_directory dir;
+		dir.set_timestamp(timestamp);
+		new_entry.add_resource_directory(dir);
+		entries->push_back(new_entry);
+		it = entries->end() - 1;
+	}
+
+	//Search for data resource entry by language
+	entries = &(*it).get_resource_directory().get_entry_list();
+	it = std::find_if(entries->begin(), entries->end(), resource_directory::id_entry_finder(language));
+	if(it != entries->end())
+		entries->erase(it); //Erase it, if found
+
+	//Add new data entry
+	resource_directory_entry new_dir_data_entry;
+	resource_data_entry data_dir(data, codepage);
+	new_dir_data_entry.add_data_entry(data_dir);
+	new_dir_data_entry.set_id(language);
+	entries->push_back(new_dir_data_entry);
+}
+
+//Adds resource. If resource already exists, replaces it
+void pe_resource_manager::add_resource(const std::string& data, resource_type type, const std::wstring& name, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_entry;
+	new_entry.set_name(name);
+
+	add_resource(data, type, new_entry, resource_directory::entry_finder(name), language, codepage, timestamp);
+}
+
+//Adds resource. If resource already exists, replaces it
+void pe_resource_manager::add_resource(const std::string& data, const std::wstring& root_name, const std::wstring& name, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_entry;
+	new_entry.set_name(name);
+
+	add_resource(data, root_name, new_entry, resource_directory::entry_finder(name), language, codepage, timestamp);
+}
+
+//Adds resource. If resource already exists, replaces it
+void pe_resource_manager::add_resource(const std::string& data, resource_type type, uint32_t id, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_entry;
+	new_entry.set_id(id);
+
+	add_resource(data, type, new_entry, resource_directory::entry_finder(id), language, codepage, timestamp);
+}
+
+//Adds resource. If resource already exists, replaces it
+void pe_resource_manager::add_resource(const std::string& data, const std::wstring& root_name, uint32_t id, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_entry;
+	new_entry.set_id(id);
+
+	add_resource(data, root_name, new_entry, resource_directory::entry_finder(id), language, codepage, timestamp);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_resource_manager.h b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_manager.h
new file mode 100644
index 0000000000000000000000000000000000000000..d40a48de8b222a0855fb1937e397821acfd7ada3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_manager.h
@@ -0,0 +1,95 @@
+#ifndef pebliss_pe_resource_manager_h
+#define pebliss_pe_resource_manager_h
+#pragma once
+#include <map>
+#include <sstream>
+#include <string>
+#include <memory>
+#include "pe_base.h"
+#include "pe_structures.h"
+#include "pe_resources.h"
+#include "message_table.h"
+#include "file_version_info.h"
+#include "pe_resource_viewer.h"
+#include "resource_data_info.h"
+
+namespace pe_bliss
+{
+//Derived class to edit PE resources
+class pe_resource_manager : public pe_resource_viewer
+{
+public:
+	//Constructor from root resource directory
+	explicit pe_resource_manager(resource_directory& root_directory);
+	
+	resource_directory& get_root_directory();
+
+public: //Resource editing
+	//Removes all resources of given type or root name
+	//If there's more than one directory entry of a given type, only the
+	//first one will be deleted (that's an unusual situation)
+	//Returns true if resource was deleted
+	bool remove_resource_type(resource_type type);
+	bool remove_resource(const std::wstring& root_name);
+	
+	//Removes all resource languages by resource type/root name and name
+	//Deletes only one entry of given type and name
+	//Returns true if resource was deleted
+	bool remove_resource(resource_type type, const std::wstring& name);
+	bool remove_resource(const std::wstring& root_name, const std::wstring& name);
+	//Removes all resource languages by resource type/root name and ID
+	//Deletes only one entry of given type and ID
+	//Returns true if resource was deleted
+	bool remove_resource(resource_type type, uint32_t id);
+	bool remove_resource(const std::wstring& root_name, uint32_t id);
+
+	//Removes resource language by resource type/root name and name
+	//Deletes only one entry of given type, name and language
+	//Returns true if resource was deleted
+	bool remove_resource(resource_type type, const std::wstring& name, uint32_t language);
+	bool remove_resource(const std::wstring& root_name, const std::wstring& name, uint32_t language);
+	//Removes recource language by resource type/root name and ID
+	//Deletes only one entry of given type, ID and language
+	//Returns true if resource was deleted
+	bool remove_resource(resource_type type, uint32_t id, uint32_t language);
+	bool remove_resource(const std::wstring& root_name, uint32_t id, uint32_t language);
+	
+	//Adds resource. If resource already exists, replaces it
+	//timestamp will be used for directories that will be added
+	void add_resource(const std::string& data, resource_type type, const std::wstring& name, uint32_t language, uint32_t codepage = 0, uint32_t timestamp = 0);
+	void add_resource(const std::string& data, const std::wstring& root_name, const std::wstring& name, uint32_t language, uint32_t codepage = 0, uint32_t timestamp = 0);
+	//Adds resource. If resource already exists, replaces it
+	//timestamp will be used for directories that will be added
+	void add_resource(const std::string& data, resource_type type, uint32_t id, uint32_t language, uint32_t codepage = 0, uint32_t timestamp = 0);
+	void add_resource(const std::string& data, const std::wstring& root_name, uint32_t id, uint32_t language, uint32_t codepage = 0, uint32_t timestamp = 0);
+
+public:
+	//Helpers to add/replace resource
+	void add_resource(const std::string& data, resource_type type,
+		resource_directory_entry& new_entry,
+		const resource_directory::entry_finder& finder,
+		uint32_t language, uint32_t codepage, uint32_t timestamp);
+
+	void add_resource(const std::string& data, const std::wstring& root_name,
+		resource_directory_entry& new_entry,
+		const resource_directory::entry_finder& finder,
+		uint32_t language, uint32_t codepage, uint32_t timestamp);
+
+	void add_resource(const std::string& data, resource_directory_entry& new_root_entry,
+		const resource_directory::entry_finder& root_finder,
+		resource_directory_entry& new_entry,
+		const resource_directory::entry_finder& finder,
+		uint32_t language, uint32_t codepage, uint32_t timestamp);
+
+private:
+	//Root resource directory. We're not copying it, because it might be heavy
+	resource_directory& root_dir_edit_;
+
+	//Helper to remove resource
+	bool remove_resource(const resource_directory::entry_finder& root_finder, const resource_directory::entry_finder& finder);
+
+	//Helper to remove resource
+	bool remove_resource(const resource_directory::entry_finder& root_finder, const resource_directory::entry_finder& finder, uint32_t language);
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_resource_viewer.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_viewer.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1414c33feda1720bf43cc4a1e124df9f766ab742
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_viewer.cpp
@@ -0,0 +1,361 @@
+#include <algorithm>
+#include <cmath>
+#include "pe_resource_viewer.h"
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Constructor from root resource_directory
+pe_resource_viewer::pe_resource_viewer(const resource_directory& root_directory)
+	:root_dir_(root_directory)
+{}
+
+const resource_directory& pe_resource_viewer::get_root_directory() const
+{
+	return root_dir_;
+}
+
+//Finder helpers
+bool pe_resource_viewer::has_name::operator()(const resource_directory_entry& entry) const
+{
+	return entry.is_named();
+}
+
+bool pe_resource_viewer::has_id::operator()(const resource_directory_entry& entry) const
+{
+	return !entry.is_named();
+}
+
+//Lists resource types existing in PE file (non-named only)
+const pe_resource_viewer::resource_type_list pe_resource_viewer::list_resource_types() const
+{
+	resource_type_list ret;
+
+	//Get root directory entries list
+	const resource_directory::entry_list& entries = root_dir_.get_entry_list();
+	for(resource_directory::entry_list::const_iterator it = entries.begin(); it != entries.end(); ++it)
+	{
+		//List all non-named items
+		if(!(*it).is_named())
+			ret.push_back((*it).get_id());
+	}
+
+	return ret;
+}
+
+//Returns true if resource type exists
+bool pe_resource_viewer::resource_exists(resource_type type) const
+{
+	const resource_directory::entry_list& entries = root_dir_.get_entry_list();
+	return std::find_if(entries.begin(), entries.end(), resource_directory::id_entry_finder(type)) != entries.end();
+}
+
+//Returns true if resource name exists
+bool pe_resource_viewer::resource_exists(const std::wstring& root_name) const
+{
+	const resource_directory::entry_list& entries = root_dir_.get_entry_list();
+	return std::find_if(entries.begin(), entries.end(), resource_directory::name_entry_finder(root_name)) != entries.end();
+}
+
+//Helper function to get name list from entry list
+const pe_resource_viewer::resource_name_list pe_resource_viewer::get_name_list(const resource_directory::entry_list& entries)
+{
+	resource_name_list ret;
+
+	for(resource_directory::entry_list::const_iterator it = entries.begin(); it != entries.end(); ++it)
+	{
+		//List all named items
+		if((*it).is_named())
+			ret.push_back((*it).get_name());
+	}
+
+	return ret;
+}
+
+//Helper function to get ID list from entry list
+const pe_resource_viewer::resource_id_list pe_resource_viewer::get_id_list(const resource_directory::entry_list& entries)
+{
+	resource_id_list ret;
+
+	for(resource_directory::entry_list::const_iterator it = entries.begin(); it != entries.end(); ++it)
+	{
+		//List all non-named items
+		if(!(*it).is_named())
+			ret.push_back((*it).get_id());
+	}
+
+	return ret;
+}
+
+//Lists resource names existing in PE file by resource type
+const pe_resource_viewer::resource_name_list pe_resource_viewer::list_resource_names(resource_type type) const
+{
+	return get_name_list(root_dir_.entry_by_id(type).get_resource_directory().get_entry_list());
+}
+
+//Lists resource names existing in PE file by resource name
+const pe_resource_viewer::resource_name_list pe_resource_viewer::list_resource_names(const std::wstring& root_name) const
+{
+	return get_name_list(root_dir_.entry_by_name(root_name).get_resource_directory().get_entry_list());
+}
+
+//Lists resource IDs existing in PE file by resource type
+const pe_resource_viewer::resource_id_list pe_resource_viewer::list_resource_ids(resource_type type) const
+{
+	return get_id_list(root_dir_.entry_by_id(type).get_resource_directory().get_entry_list());
+}
+
+//Lists resource IDs existing in PE file by resource name
+const pe_resource_viewer::resource_id_list pe_resource_viewer::list_resource_ids(const std::wstring& root_name) const
+{
+	return get_id_list(root_dir_.entry_by_name(root_name).get_resource_directory().get_entry_list());
+}
+
+//Returns resource count by type
+unsigned long pe_resource_viewer::get_resource_count(resource_type type) const
+{
+	return static_cast<unsigned long>(
+		root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.get_entry_list()
+		.size());
+}
+
+//Returns resource count by name
+unsigned long pe_resource_viewer::get_resource_count(const std::wstring& root_name) const
+{
+	return static_cast<unsigned long>(
+		root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.get_entry_list()
+		.size());
+}
+
+//Returns language count of resource by resource type and name
+unsigned long pe_resource_viewer::get_language_count(resource_type type, const std::wstring& name) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return static_cast<unsigned long>(std::count_if(entries.begin(), entries.end(), has_id()));
+}
+
+//Returns language count of resource by resource names
+unsigned long pe_resource_viewer::get_language_count(const std::wstring& root_name, const std::wstring& name) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return static_cast<unsigned long>(std::count_if(entries.begin(), entries.end(), has_id()));
+}
+
+//Returns language count of resource by resource type and ID
+unsigned long pe_resource_viewer::get_language_count(resource_type type, uint32_t id) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return static_cast<unsigned long>(std::count_if(entries.begin(), entries.end(), has_id()));
+}
+
+//Returns language count of resource by resource name and ID
+unsigned long pe_resource_viewer::get_language_count(const std::wstring& root_name, uint32_t id) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return static_cast<unsigned long>(std::count_if(entries.begin(), entries.end(), has_id()));
+}
+
+//Lists resource languages by resource type and name
+const pe_resource_viewer::resource_language_list pe_resource_viewer::list_resource_languages(resource_type type, const std::wstring& name) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return get_id_list(entries);
+}
+
+//Lists resource languages by resource names
+const pe_resource_viewer::resource_language_list pe_resource_viewer::list_resource_languages(const std::wstring& root_name, const std::wstring& name) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return get_id_list(entries);
+}
+
+//Lists resource languages by resource type and ID
+const pe_resource_viewer::resource_language_list pe_resource_viewer::list_resource_languages(resource_type type, uint32_t id) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return get_id_list(entries);
+}
+
+//Lists resource languages by resource name and ID
+const pe_resource_viewer::resource_language_list pe_resource_viewer::list_resource_languages(const std::wstring& root_name, uint32_t id) const
+{
+	const resource_directory::entry_list& entries =
+		root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	return get_id_list(entries);
+}
+
+//Returns raw resource data by type, name and language
+const resource_data_info pe_resource_viewer::get_resource_data_by_name(uint32_t language, resource_type type, const std::wstring& name) const
+{
+	return resource_data_info(root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.entry_by_id(language)
+		.get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by root name, name and language
+const resource_data_info pe_resource_viewer::get_resource_data_by_name(uint32_t language, const std::wstring& root_name, const std::wstring& name) const
+{
+	return resource_data_info(root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.entry_by_id(language)
+		.get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by type, ID and language
+const resource_data_info pe_resource_viewer::get_resource_data_by_id(uint32_t language, resource_type type, uint32_t id) const
+{
+	return resource_data_info(root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.entry_by_id(language)
+		.get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by root name, ID and language
+const resource_data_info pe_resource_viewer::get_resource_data_by_id(uint32_t language, const std::wstring& root_name, uint32_t id) const
+{
+	return resource_data_info(root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.entry_by_id(language)
+		.get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by type, name and index in language directory (instead of language)
+const resource_data_info pe_resource_viewer::get_resource_data_by_name(resource_type type, const std::wstring& name, uint32_t index) const
+{
+	const resource_directory::entry_list& entries = root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	if(entries.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+
+	return resource_data_info(entries.at(index).get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by root name, name and index in language directory (instead of language)
+const resource_data_info pe_resource_viewer::get_resource_data_by_name(const std::wstring& root_name, const std::wstring& name, uint32_t index) const
+{
+	const resource_directory::entry_list& entries = root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_name(name)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	if(entries.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+
+	return resource_data_info(entries.at(index).get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by type, ID and index in language directory (instead of language)
+const resource_data_info pe_resource_viewer::get_resource_data_by_id(resource_type type, uint32_t id, uint32_t index) const
+{
+	const resource_directory::entry_list& entries = root_dir_ //Type directory
+		.entry_by_id(type)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	if(entries.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+
+	return resource_data_info(entries.at(index).get_data_entry()); //Data directory
+}
+
+//Returns raw resource data by root name, ID and index in language directory (instead of language)
+const resource_data_info pe_resource_viewer::get_resource_data_by_id(const std::wstring& root_name, uint32_t id, uint32_t index) const
+{
+	const resource_directory::entry_list& entries = root_dir_ //Type directory
+		.entry_by_name(root_name)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(id)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	if(entries.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+
+	return resource_data_info(entries.at(index).get_data_entry()); //Data directory
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_resource_viewer.h b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_viewer.h
new file mode 100644
index 0000000000000000000000000000000000000000..d68fb105c6884bc914afbd2cc8274379b26209c0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_resource_viewer.h
@@ -0,0 +1,135 @@
+#ifndef pebliss_pe_resource_viewer_h
+#define pebliss_pe_resource_viewer_h
+#pragma once
+#include <map>
+#include <string>
+#include "pe_structures.h"
+#include "pe_resources.h"
+#include "message_table.h"
+#include "resource_data_info.h"
+
+namespace pe_bliss
+{
+	//PE resource manager allows to read resources from PE files
+class pe_resource_viewer
+{
+public:
+	//Resource type enumeration
+	enum resource_type
+	{
+		resource_cursor = 1,
+		resource_bitmap = 2,
+		resource_icon = 3,
+		resource_menu = 4,
+		resource_dialog = 5,
+		resource_string = 6,
+		resource_fontdir = 7,
+		resource_font = 8,
+		resource_accelerator = 9,
+		resource_rcdata = 10,
+		resource_message_table = 11,
+		resource_cursor_group = 12,
+		resource_icon_group = 14,
+		resource_version = 16,
+		resource_dlginclude = 17,
+		resource_plugplay = 19,
+		resource_vxd = 20,
+		resource_anicursor = 21,
+		resource_aniicon = 22,
+		resource_html = 23,
+		resource_manifest = 24
+	};
+
+public:
+	//Some useful typedefs
+	typedef std::vector<uint32_t> resource_type_list;
+	typedef std::vector<uint32_t> resource_id_list;
+	typedef std::vector<std::wstring> resource_name_list;
+	typedef std::vector<uint32_t> resource_language_list;
+	
+public:
+	//Constructor from root resource_directory from PE file
+	explicit pe_resource_viewer(const resource_directory& root_directory);
+
+	const resource_directory& get_root_directory() const;
+
+	//Lists resource types existing in PE file (non-named only)
+	const resource_type_list list_resource_types() const;
+	//Returns true if resource type exists
+	bool resource_exists(resource_type type) const;
+	//Returns true if resource name exists
+	bool resource_exists(const std::wstring& root_name) const;
+
+	//Lists resource names existing in PE file by resource type
+	const resource_name_list list_resource_names(resource_type type) const;
+	//Lists resource names existing in PE file by resource name
+	const resource_name_list list_resource_names(const std::wstring& root_name) const;
+	//Lists resource IDs existing in PE file by resource type
+	const resource_id_list list_resource_ids(resource_type type) const;
+	//Lists resource IDs existing in PE file by resource name
+	const resource_id_list list_resource_ids(const std::wstring& root_name) const;
+	//Returns resource count by type
+	unsigned long get_resource_count(resource_type type) const;
+	//Returns resource count by name
+	unsigned long get_resource_count(const std::wstring& root_name) const;
+
+	//Returns language count of resource by resource type and name
+	unsigned long get_language_count(resource_type type, const std::wstring& name) const;
+	//Returns language count of resource by resource names
+	unsigned long get_language_count(const std::wstring& root_name, const std::wstring& name) const;
+	//Returns language count of resource by resource type and ID
+	unsigned long get_language_count(resource_type type, uint32_t id) const;
+	//Returns language count of resource by resource name and ID
+	unsigned long get_language_count(const std::wstring& root_name, uint32_t id) const;
+	//Lists resource languages by resource type and name
+	const resource_language_list list_resource_languages(resource_type type, const std::wstring& name) const;
+	//Lists resource languages by resource names
+	const resource_language_list list_resource_languages(const std::wstring& root_name, const std::wstring& name) const;
+	//Lists resource languages by resource type and ID
+	const resource_language_list list_resource_languages(resource_type type, uint32_t id) const;
+	//Lists resource languages by resource name and ID
+	const resource_language_list list_resource_languages(const std::wstring& root_name, uint32_t id) const;
+
+	//Returns raw resource data by type, name and language
+	const resource_data_info get_resource_data_by_name(uint32_t language, resource_type type, const std::wstring& name) const;
+	//Returns raw resource data by root name, name and language
+	const resource_data_info get_resource_data_by_name(uint32_t language, const std::wstring& root_name, const std::wstring& name) const;
+	//Returns raw resource data by type, ID and language
+	const resource_data_info get_resource_data_by_id(uint32_t language, resource_type type, uint32_t id) const;
+	//Returns raw resource data by root name, ID and language
+	const resource_data_info get_resource_data_by_id(uint32_t language, const std::wstring& root_name, uint32_t id) const;
+	//Returns raw resource data by type, name and index in language directory (instead of language)
+	const resource_data_info get_resource_data_by_name(resource_type type, const std::wstring& name, uint32_t index = 0) const;
+	//Returns raw resource data by root name, name and index in language directory (instead of language)
+	const resource_data_info get_resource_data_by_name(const std::wstring& root_name, const std::wstring& name, uint32_t index = 0) const;
+	//Returns raw resource data by type, ID and index in language directory (instead of language)
+	const resource_data_info get_resource_data_by_id(resource_type type, uint32_t id, uint32_t index = 0) const;
+	//Returns raw resource data by root name, ID and index in language directory (instead of language)
+	const resource_data_info get_resource_data_by_id(const std::wstring& root_name, uint32_t id, uint32_t index = 0) const;
+
+protected:
+	//Root resource directory. We're not copying it, because it might be heavy
+	const resource_directory& root_dir_;
+
+	//Helper function to get ID list from entry list
+	static const resource_id_list get_id_list(const resource_directory::entry_list& entries);
+	//Helper function to get name list from entry list
+	static const resource_name_list get_name_list(const resource_directory::entry_list& entries);
+
+protected:
+	//Helper structure - finder of resource_directory_entry that is named
+	struct has_name
+	{
+	public:
+		bool operator()(const resource_directory_entry& entry) const;
+	};
+
+	//Helper structure - finder of resource_directory_entry that is not named (has id)
+	struct has_id
+	{
+	public:
+		bool operator()(const resource_directory_entry& entry) const;
+	};
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_resources.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_resources.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a819c7bb719d7b34f08b3ed464dddda168aa6357
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_resources.cpp
@@ -0,0 +1,705 @@
+#include <algorithm>
+#include <string.h>
+#include "pe_resources.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//RESOURCES
+//Default constructor
+resource_data_entry::resource_data_entry()
+	:codepage_(0)
+{}
+
+//Constructor from data
+resource_data_entry::resource_data_entry(const std::string& data, uint32_t codepage)
+	:codepage_(codepage), data_(data)
+{}
+
+//Returns resource data codepage
+uint32_t resource_data_entry::get_codepage() const
+{
+	return codepage_;
+}
+
+//Returns resource data
+const std::string& resource_data_entry::get_data() const
+{
+	return data_;
+}
+
+//Sets resource data codepage
+void resource_data_entry::set_codepage(uint32_t codepage)
+{
+	codepage_ = codepage;
+}
+
+//Sets resource data
+void resource_data_entry::set_data(const std::string& data)
+{
+	data_ = data;
+}
+
+//Default constructor
+resource_directory_entry::includes::includes()
+	:data_(0)
+{}
+
+//Default constructor
+resource_directory_entry::resource_directory_entry()
+	:id_(0), includes_data_(false), named_(false)
+{}
+
+//Copy constructor
+resource_directory_entry::resource_directory_entry(const resource_directory_entry& other)
+	:id_(other.id_), name_(other.name_), includes_data_(other.includes_data_), named_(other.named_)
+{
+	//If union'ed pointer is not zero
+	if(other.ptr_.data_)
+	{
+		if(other.includes_data())
+			ptr_.data_ = new resource_data_entry(*other.ptr_.data_);
+		else
+			ptr_.dir_ = new resource_directory(*other.ptr_.dir_);
+	}
+}
+
+//Copy assignment operator
+resource_directory_entry& resource_directory_entry::operator=(const resource_directory_entry& other)
+{
+	release();
+
+	id_ = other.id_;
+	name_ = other.name_;
+	includes_data_ = other.includes_data_;
+	named_ = other.named_;
+
+	//If other union'ed pointer is not zero
+	if(other.ptr_.data_)
+	{
+		if(other.includes_data())
+			ptr_.data_ = new resource_data_entry(*other.ptr_.data_);
+		else
+			ptr_.dir_ = new resource_directory(*other.ptr_.dir_);
+	}
+
+	return *this;
+}
+
+//Destroys included data
+void resource_directory_entry::release()
+{
+	//If union'ed pointer is not zero
+	if(ptr_.data_)
+	{
+		if(includes_data())
+			delete ptr_.data_;
+		else
+			delete ptr_.dir_;
+
+		ptr_.data_ = 0;
+	}
+}
+
+//Destructor
+resource_directory_entry::~resource_directory_entry()
+{
+	release();
+}
+
+//Returns entry ID
+uint32_t resource_directory_entry::get_id() const
+{
+	return id_;
+}
+
+//Returns entry name
+const std::wstring& resource_directory_entry::get_name() const
+{
+	return name_;
+}
+
+//Returns true, if entry has name
+//Returns false, if entry has ID
+bool resource_directory_entry::is_named() const
+{
+	return named_;
+}
+
+//Returns true, if entry includes resource_data_entry
+//Returns false, if entry includes resource_directory
+bool resource_directory_entry::includes_data() const
+{
+	return includes_data_;
+}
+
+//Returns resource_directory if entry includes it, otherwise throws an exception
+const resource_directory& resource_directory_entry::get_resource_directory() const
+{
+	if(!ptr_.dir_ || includes_data_)
+		throw pe_exception("Resource directory entry does not contain resource directory", pe_exception::resource_directory_entry_error);
+
+	return *ptr_.dir_;
+}
+
+//Returns resource_data_entry if entry includes it, otherwise throws an exception
+const resource_data_entry& resource_directory_entry::get_data_entry() const
+{
+	if(!ptr_.data_ || !includes_data_)
+		throw pe_exception("Resource directory entry does not contain resource data entry", pe_exception::resource_directory_entry_error);
+
+	return *ptr_.data_;
+}
+
+//Returns resource_directory if entry includes it, otherwise throws an exception
+resource_directory& resource_directory_entry::get_resource_directory()
+{
+	if(!ptr_.dir_ || includes_data_)
+		throw pe_exception("Resource directory entry does not contain resource directory", pe_exception::resource_directory_entry_error);
+
+	return *ptr_.dir_;
+}
+
+//Returns resource_data_entry if entry includes it, otherwise throws an exception
+resource_data_entry& resource_directory_entry::get_data_entry()
+{
+	if(!ptr_.data_ || !includes_data_)
+		throw pe_exception("Resource directory entry does not contain resource data entry", pe_exception::resource_directory_entry_error);
+
+	return *ptr_.data_;
+}
+
+//Sets entry name
+void resource_directory_entry::set_name(const std::wstring& name)
+{
+	name_ = name;
+	named_ = true;
+	id_ = 0;
+}
+
+//Sets entry ID
+void resource_directory_entry::set_id(uint32_t id)
+{
+	id_ = id;
+	named_ = false;
+	name_.clear();
+}
+
+//Adds resource_data_entry
+void resource_directory_entry::add_data_entry(const resource_data_entry& entry)
+{
+	release();
+	ptr_.data_ = new resource_data_entry(entry);
+	includes_data_ = true;
+}
+
+//Adds resource_directory
+void resource_directory_entry::add_resource_directory(const resource_directory& dir)
+{
+	release();
+	ptr_.dir_ = new resource_directory(dir);
+	includes_data_ = false;
+}
+
+//Default constructor
+resource_directory::resource_directory()
+	:characteristics_(0),
+	timestamp_(0),
+	major_version_(0), minor_version_(0),
+	number_of_named_entries_(0), number_of_id_entries_(0)
+{}
+
+//Constructor from data
+resource_directory::resource_directory(const image_resource_directory& dir)
+	:characteristics_(dir.Characteristics),
+	timestamp_(dir.TimeDateStamp),
+	major_version_(dir.MajorVersion), minor_version_(dir.MinorVersion),
+	number_of_named_entries_(0), number_of_id_entries_(0) //Set to zero here, calculate on add
+{}
+
+//Returns characteristics of directory
+uint32_t resource_directory::get_characteristics() const
+{
+	return characteristics_;
+}
+
+//Returns date and time stamp of directory
+uint32_t resource_directory::get_timestamp() const
+{
+	return timestamp_;
+}
+
+//Returns major version of directory
+uint16_t resource_directory::get_major_version() const
+{
+	return major_version_;
+}
+
+//Returns minor version of directory
+uint16_t resource_directory::get_minor_version() const
+{
+	return minor_version_;
+}
+
+//Returns number of named entries
+uint32_t resource_directory::get_number_of_named_entries() const
+{
+	return number_of_named_entries_;
+}
+
+//Returns number of ID entries
+uint32_t resource_directory::get_number_of_id_entries() const
+{
+	return number_of_id_entries_;
+}
+
+//Returns resource_directory_entry array
+const resource_directory::entry_list& resource_directory::get_entry_list() const
+{
+	return entries_;
+}
+
+//Returns resource_directory_entry array
+resource_directory::entry_list& resource_directory::get_entry_list()
+{
+	return entries_;
+}
+
+//Adds resource_directory_entry
+void resource_directory::add_resource_directory_entry(const resource_directory_entry& entry)
+{
+	entries_.push_back(entry);
+	if(entry.is_named())
+		++number_of_named_entries_;
+	else
+		++number_of_id_entries_;
+}
+
+//Clears resource_directory_entry array
+void resource_directory::clear_resource_directory_entry_list()
+{
+	entries_.clear();
+	number_of_named_entries_ = 0;
+	number_of_id_entries_ = 0;
+}
+
+//Sets characteristics of directory
+void resource_directory::set_characteristics(uint32_t characteristics)
+{
+	characteristics_ = characteristics;
+}
+
+//Sets date and time stamp of directory
+void resource_directory::set_timestamp(uint32_t timestamp)
+{
+	timestamp_ = timestamp;
+}
+
+//Sets number of named entries
+void resource_directory::set_number_of_named_entries(uint32_t number)
+{
+	number_of_named_entries_ = number;
+}
+
+//Sets number of ID entries
+void resource_directory::set_number_of_id_entries(uint32_t number)
+{
+	number_of_id_entries_ = number;
+}
+
+//Sets major version of directory
+void resource_directory::set_major_version(uint16_t major_version)
+{
+	major_version_ = major_version;
+}
+
+//Sets minor version of directory
+void resource_directory::get_minor_version(uint16_t minor_version)
+{
+	minor_version_ = minor_version;
+}
+
+//Processes resource directory
+const resource_directory process_resource_directory(const pe_base& pe, uint32_t res_rva, uint32_t offset_to_directory, std::set<uint32_t>& processed)
+{
+	resource_directory ret;
+	
+	//Check for resource loops
+	if(!processed.insert(offset_to_directory).second)
+		throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+	if(!pe_utils::is_sum_safe(res_rva, offset_to_directory))
+		throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+	//Get root IMAGE_RESOURCE_DIRECTORY
+	image_resource_directory directory = pe.section_data_from_rva<image_resource_directory>(res_rva + offset_to_directory, section_data_virtual, true);
+
+	ret = resource_directory(directory);
+
+	//Check DWORDs for possible overflows
+	if(!pe_utils::is_sum_safe(directory.NumberOfIdEntries, directory.NumberOfNamedEntries)
+		|| directory.NumberOfIdEntries + directory.NumberOfNamedEntries >= pe_utils::max_dword / sizeof(image_resource_directory_entry) + sizeof(image_resource_directory))
+		throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+	if(!pe_utils::is_sum_safe(offset_to_directory, sizeof(image_resource_directory) + (directory.NumberOfIdEntries + directory.NumberOfNamedEntries) * sizeof(image_resource_directory_entry))
+		|| !pe_utils::is_sum_safe(res_rva, offset_to_directory + sizeof(image_resource_directory) + (directory.NumberOfIdEntries + directory.NumberOfNamedEntries) * sizeof(image_resource_directory_entry)))
+		throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+	for(unsigned long i = 0; i != static_cast<unsigned long>(directory.NumberOfIdEntries) + directory.NumberOfNamedEntries; ++i)
+	{
+		//Read directory entries one by one
+		image_resource_directory_entry dir_entry = pe.section_data_from_rva<image_resource_directory_entry>(
+			res_rva + sizeof(image_resource_directory) + i * sizeof(image_resource_directory_entry) + offset_to_directory, section_data_virtual, true);
+
+		//Create directory entry structure
+		resource_directory_entry entry;
+
+		//If directory is named
+		if(dir_entry.NameIsString)
+		{
+			if(!pe_utils::is_sum_safe(res_rva + sizeof(uint16_t) /* safe */, dir_entry.NameOffset))
+				throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+			//get directory name length
+			uint16_t directory_name_length = pe.section_data_from_rva<uint16_t>(res_rva + dir_entry.NameOffset, section_data_virtual, true);
+
+			//Check name length
+			if(pe.section_data_length_from_rva(res_rva + dir_entry.NameOffset + sizeof(uint16_t), res_rva + dir_entry.NameOffset + sizeof(uint16_t), section_data_virtual, true)
+				< directory_name_length)
+				throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+#ifdef PE_BLISS_WINDOWS
+			//Set entry UNICODE name
+			entry.set_name(std::wstring(
+				reinterpret_cast<const wchar_t*>(pe.section_data_from_rva(res_rva + dir_entry.NameOffset + sizeof(uint16_t), section_data_virtual, true)),
+				directory_name_length));
+#else
+			//Set entry UNICODE name
+			entry.set_name(pe_utils::from_ucs2(u16string(
+				reinterpret_cast<const unicode16_t*>(pe.section_data_from_rva(res_rva + dir_entry.NameOffset + sizeof(uint16_t), section_data_virtual, true)),
+				directory_name_length)));
+#endif
+		}
+		else
+		{
+			//Else - set directory ID
+			entry.set_id(dir_entry.Id);
+		}
+
+		//If directory entry has another resource directory
+		if(dir_entry.DataIsDirectory)
+		{
+			entry.add_resource_directory(process_resource_directory(pe, res_rva, dir_entry.OffsetToDirectory, processed));
+		}
+		else
+		{
+			//If directory entry has data
+			image_resource_data_entry data_entry = pe.section_data_from_rva<image_resource_data_entry>(
+				res_rva + dir_entry.OffsetToData, section_data_virtual, true);
+
+			//Check byte count that stated by data entry
+			if(pe.section_data_length_from_rva(data_entry.OffsetToData, data_entry.OffsetToData, section_data_virtual, true) < data_entry.Size)
+				throw pe_exception("Incorrect resource directory", pe_exception::incorrect_resource_directory);
+
+			//Add data entry to directory entry
+			entry.add_data_entry(resource_data_entry(
+				std::string(pe.section_data_from_rva(data_entry.OffsetToData, section_data_virtual, true), data_entry.Size),
+				data_entry.CodePage));
+		}
+
+		//Save directory entry
+		ret.add_resource_directory_entry(entry);
+	}
+
+	//Return resource directory
+	return ret;
+}
+
+//Helper function to calculate needed space for resource data
+void calculate_resource_data_space(const resource_directory& root, uint32_t aligned_offset_from_section_start, uint32_t& needed_size_for_structures, uint32_t& needed_size_for_strings)
+{
+	needed_size_for_structures += sizeof(image_resource_directory);
+	for(resource_directory::entry_list::const_iterator it = root.get_entry_list().begin(); it != root.get_entry_list().end(); ++it)
+	{
+		needed_size_for_structures += sizeof(image_resource_directory_entry);
+
+		if((*it).is_named())
+			needed_size_for_strings += static_cast<uint32_t>(((*it).get_name().length() + 1) * 2 /* unicode */ + sizeof(uint16_t) /* for string length */);
+
+		if(!(*it).includes_data())
+			calculate_resource_data_space((*it).get_resource_directory(), aligned_offset_from_section_start, needed_size_for_structures, needed_size_for_strings);
+	}
+}
+
+//Helper function to calculate needed space for resource data
+void calculate_resource_data_space(const resource_directory& root, uint32_t needed_size_for_structures, uint32_t needed_size_for_strings, uint32_t& needed_size_for_data, uint32_t& current_data_pos)
+{
+	for(resource_directory::entry_list::const_iterator it = root.get_entry_list().begin(); it != root.get_entry_list().end(); ++it)
+	{
+		if((*it).includes_data())
+		{
+			uint32_t data_size = static_cast<uint32_t>((*it).get_data_entry().get_data().length()
+				+ sizeof(image_resource_data_entry)
+				+ (pe_utils::align_up(current_data_pos, sizeof(uint32_t)) - current_data_pos) /* alignment */);
+			needed_size_for_data += data_size;
+			current_data_pos += data_size;
+		}
+		else
+		{
+			calculate_resource_data_space((*it).get_resource_directory(), needed_size_for_structures, needed_size_for_strings, needed_size_for_data, current_data_pos);
+		}
+	}
+}
+
+//Helper: sorts resource directory entries
+struct entry_sorter
+{
+public:
+	bool operator()(const resource_directory_entry& entry1, const resource_directory_entry& entry2) const;
+};
+
+//Helper function to rebuild resource directory
+void rebuild_resource_directory(pe_base& pe, section& resource_section, resource_directory& root, uint32_t& current_structures_pos, uint32_t& current_data_pos, uint32_t& current_strings_pos, uint32_t offset_from_section_start)
+{
+	//Create resource directory
+	image_resource_directory dir = {0};
+	dir.Characteristics = root.get_characteristics();
+	dir.MajorVersion = root.get_major_version();
+	dir.MinorVersion = root.get_minor_version();
+	dir.TimeDateStamp = root.get_timestamp();
+	
+	{
+		resource_directory::entry_list& entries = root.get_entry_list();
+		std::sort(entries.begin(), entries.end(), entry_sorter());
+	}
+
+	//Calculate number of named and ID entries
+	for(resource_directory::entry_list::const_iterator it = root.get_entry_list().begin(); it != root.get_entry_list().end(); ++it)
+	{
+		if((*it).is_named())
+			++dir.NumberOfNamedEntries;
+		else
+			++dir.NumberOfIdEntries;
+	}
+	
+	std::string& raw_data = resource_section.get_raw_data();
+
+	//Save resource directory
+	memcpy(&raw_data[current_structures_pos], &dir, sizeof(dir));
+	current_structures_pos += sizeof(dir);
+
+	uint32_t this_current_structures_pos = current_structures_pos;
+
+	current_structures_pos += sizeof(image_resource_directory_entry) * (dir.NumberOfNamedEntries + dir.NumberOfIdEntries);
+
+	//Create all resource directory entries
+	for(resource_directory::entry_list::iterator it = root.get_entry_list().begin(); it != root.get_entry_list().end(); ++it)
+	{
+		image_resource_directory_entry entry;
+		if((*it).is_named())
+		{
+			entry.Name = 0x80000000 | (current_strings_pos - offset_from_section_start);
+			uint16_t unicode_length = static_cast<uint16_t>((*it).get_name().length());
+			memcpy(&raw_data[current_strings_pos], &unicode_length, sizeof(unicode_length));
+			current_strings_pos += sizeof(unicode_length);
+
+#ifdef PE_BLISS_WINDOWS
+			memcpy(&raw_data[current_strings_pos], (*it).get_name().c_str(), (*it).get_name().length() * sizeof(uint16_t) + sizeof(uint16_t) /* unicode */);
+#else
+			{
+				u16string str(pe_utils::to_ucs2((*it).get_name()));
+				memcpy(&raw_data[current_strings_pos], str.c_str(), (*it).get_name().length() * sizeof(uint16_t) + sizeof(uint16_t) /* unicode */);
+			}
+#endif
+
+			current_strings_pos += static_cast<unsigned long>((*it).get_name().length() * sizeof(uint16_t) + sizeof(uint16_t) /* unicode */);
+		}
+		else
+		{
+			entry.Name = (*it).get_id();
+		}
+
+		if((*it).includes_data())
+		{
+			current_data_pos = pe_utils::align_up(current_data_pos, sizeof(uint32_t));
+			image_resource_data_entry data_entry = {0};
+			data_entry.CodePage = (*it).get_data_entry().get_codepage();
+			data_entry.Size = static_cast<uint32_t>((*it).get_data_entry().get_data().length());
+			data_entry.OffsetToData = pe.rva_from_section_offset(resource_section, current_data_pos + sizeof(data_entry));
+			
+			entry.OffsetToData = current_data_pos - offset_from_section_start;
+
+			memcpy(&raw_data[current_data_pos], &data_entry, sizeof(data_entry));
+			current_data_pos += sizeof(data_entry);
+			
+			memcpy(&raw_data[current_data_pos], (*it).get_data_entry().get_data().data(), data_entry.Size);
+			current_data_pos += data_entry.Size;
+
+			memcpy(&raw_data[this_current_structures_pos], &entry, sizeof(entry));
+			this_current_structures_pos += sizeof(entry);
+		}
+		else
+		{
+			entry.OffsetToData = 0x80000000 | (current_structures_pos - offset_from_section_start);
+
+			memcpy(&raw_data[this_current_structures_pos], &entry, sizeof(entry));
+			this_current_structures_pos += sizeof(entry);
+
+			rebuild_resource_directory(pe, resource_section, (*it).get_resource_directory(), current_structures_pos, current_data_pos, current_strings_pos, offset_from_section_start);
+		}
+	}
+}
+
+//Helper function to rebuild resource directory
+bool entry_sorter::operator()(const resource_directory_entry& entry1, const resource_directory_entry& entry2) const
+{
+	if(entry1.is_named() && entry2.is_named())
+		return entry1.get_name() < entry2.get_name();
+	else if(!entry1.is_named() && !entry2.is_named())
+		return entry1.get_id() < entry2.get_id();
+	else
+		return entry1.is_named();
+}
+
+//Resources rebuilder
+//resource_directory - root resource directory
+//resources_section - section where resource directory will be placed (must be attached to PE image)
+//offset_from_section_start - offset from resources_section raw data start
+//resource_directory is non-constant, because it will be sorted
+//save_to_pe_headers - if true, new resource directory information will be saved to PE image headers
+//auto_strip_last_section - if true and resources are placed in the last section, it will be automatically stripped
+//number_of_id_entries and number_of_named_entries for resource directories are recalculated and not used
+const image_directory rebuild_resources(pe_base& pe, resource_directory& info, section& resources_section, uint32_t offset_from_section_start, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	//Check that resources_section is attached to this PE image
+	if(!pe.section_attached(resources_section))
+		throw pe_exception("Resource section must be attached to PE file", pe_exception::section_is_not_attached);
+	
+	//Check resource directory correctness
+	if(info.get_entry_list().empty())
+		throw pe_exception("Empty resource directory", pe_exception::incorrect_resource_directory);
+	
+	uint32_t aligned_offset_from_section_start = pe_utils::align_up(offset_from_section_start, sizeof(uint32_t));
+	uint32_t needed_size_for_structures = aligned_offset_from_section_start - offset_from_section_start; //Calculate needed size for resource tables and data
+	uint32_t needed_size_for_strings = 0;
+	uint32_t needed_size_for_data = 0;
+
+	calculate_resource_data_space(info, aligned_offset_from_section_start, needed_size_for_structures, needed_size_for_strings);
+
+	{
+		uint32_t current_data_pos = aligned_offset_from_section_start + needed_size_for_structures + needed_size_for_strings;
+		calculate_resource_data_space(info, needed_size_for_structures, needed_size_for_strings, needed_size_for_data, current_data_pos);
+	}
+
+	uint32_t needed_size = needed_size_for_structures + needed_size_for_strings + needed_size_for_data;
+
+	//Check if resources_section is last one. If it's not, check if there's enough place for resource data
+	if(&resources_section != &*(pe.get_image_sections().end() - 1) && 
+		(resources_section.empty() || pe_utils::align_up(resources_section.get_size_of_raw_data(), pe.get_file_alignment())
+		< needed_size + aligned_offset_from_section_start))
+		throw pe_exception("Insufficient space for resource directory", pe_exception::insufficient_space);
+
+	std::string& raw_data = resources_section.get_raw_data();
+
+	//This will be done only if resources_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + aligned_offset_from_section_start)
+		raw_data.resize(needed_size + aligned_offset_from_section_start); //Expand section raw data
+
+	uint32_t current_structures_pos = aligned_offset_from_section_start;
+	uint32_t current_strings_pos = current_structures_pos + needed_size_for_structures;
+	uint32_t current_data_pos = current_strings_pos + needed_size_for_strings;
+	rebuild_resource_directory(pe, resources_section, info, current_structures_pos, current_data_pos, current_strings_pos, aligned_offset_from_section_start);
+	
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(resources_section, auto_strip_last_section);
+
+	image_directory ret(pe.rva_from_section_offset(resources_section, aligned_offset_from_section_start), needed_size);
+
+	//If auto-rewrite of PE headers is required
+	if(save_to_pe_header)
+	{
+		pe.set_directory_rva(image_directory_entry_resource, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_resource, ret.get_size());
+	}
+
+	return ret;
+}
+
+//Returns resources from PE file
+const resource_directory get_resources(const pe_base& pe)
+{
+	resource_directory ret;
+
+	if(!pe.has_resources())
+		return ret;
+
+	//Get resource directory RVA
+	uint32_t res_rva = pe.get_directory_rva(image_directory_entry_resource);
+	
+	//Store already processed directories to avoid resource loops
+	std::set<uint32_t> processed;
+	
+	//Process all directories (recursion)
+	ret = process_resource_directory(pe, res_rva, 0, processed);
+
+	return ret;
+}
+
+//Finds resource_directory_entry by ID
+resource_directory::id_entry_finder::id_entry_finder(uint32_t id)
+	:id_(id)
+{}
+
+bool resource_directory::id_entry_finder::operator()(const resource_directory_entry& entry) const
+{
+	return !entry.is_named() && entry.get_id() == id_;
+}
+
+//Finds resource_directory_entry by name
+resource_directory::name_entry_finder::name_entry_finder(const std::wstring& name)
+	:name_(name)
+{}
+
+bool resource_directory::name_entry_finder::operator()(const resource_directory_entry& entry) const
+{
+	return entry.is_named() && entry.get_name() == name_;
+}
+
+//Finds resource_directory_entry by name or ID (universal)
+resource_directory::entry_finder::entry_finder(const std::wstring& name)
+	:name_(name), named_(true)
+{}
+
+resource_directory::entry_finder::entry_finder(uint32_t id)
+	:id_(id), named_(false)
+{}
+
+bool resource_directory::entry_finder::operator()(const resource_directory_entry& entry) const
+{
+	if(named_)
+		return entry.is_named() && entry.get_name() == name_;
+	else
+		return !entry.is_named() && entry.get_id() == id_;
+}
+
+//Returns resource_directory_entry by ID. If not found - throws an exception
+const resource_directory_entry& resource_directory::entry_by_id(uint32_t id) const
+{
+	entry_list::const_iterator i = std::find_if(entries_.begin(), entries_.end(), id_entry_finder(id));
+	if(i == entries_.end())
+		throw pe_exception("Resource directory entry not found", pe_exception::resource_directory_entry_not_found);
+
+	return *i;
+}
+
+//Returns resource_directory_entry by name. If not found - throws an exception
+const resource_directory_entry& resource_directory::entry_by_name(const std::wstring& name) const
+{
+	entry_list::const_iterator i = std::find_if(entries_.begin(), entries_.end(), name_entry_finder(name));
+	if(i == entries_.end())
+		throw pe_exception("Resource directory entry not found", pe_exception::resource_directory_entry_not_found);
+
+	return *i;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_resources.h b/irdb-lib/pebliss/trunk/pe_lib/pe_resources.h
new file mode 100644
index 0000000000000000000000000000000000000000..77cd60943dd09751b706b18993b391e0f403d0ae
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_resources.h
@@ -0,0 +1,231 @@
+#ifndef pebliss_pe_resources_h
+#define pebliss_pe_resources_h
+#pragma once
+#ifndef peresource_h
+#define peresource_h
+
+#include <vector>
+#include <string>
+#include <set>
+#include "pe_structures.h"
+#include "pe_base.h"
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Class representing resource data entry
+class resource_data_entry
+{
+public:
+	//Default constructor
+	resource_data_entry();
+	//Constructor from data
+	resource_data_entry(const std::string& data, uint32_t codepage);
+
+	//Returns resource data codepage
+	uint32_t get_codepage() const;
+	//Returns resource data
+	const std::string& get_data() const;
+		
+public: //These functions do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild resource directory
+		
+	//Sets resource data codepage
+	void set_codepage(uint32_t codepage);
+	//Sets resource data
+	void set_data(const std::string& data);
+
+private:
+	uint32_t codepage_; //Resource data codepage
+	std::string data_; //Resource data
+};
+
+//Forward declaration
+class resource_directory;
+
+//Class representing resource directory entry
+class resource_directory_entry
+{
+public:
+	//Default constructor
+	resource_directory_entry();
+	//Copy constructor
+	resource_directory_entry(const resource_directory_entry& other);
+	//Copy assignment operator
+	resource_directory_entry& operator=(const resource_directory_entry& other);
+
+	//Returns entry ID
+	uint32_t get_id() const;
+	//Returns entry name
+	const std::wstring& get_name() const;
+	//Returns true, if entry has name
+	//Returns false, if entry has ID
+	bool is_named() const;
+
+	//Returns true, if entry includes resource_data_entry
+	//Returns false, if entry includes resource_directory
+	bool includes_data() const;
+	//Returns resource_directory if entry includes it, otherwise throws an exception
+	const resource_directory& get_resource_directory() const;
+	//Returns resource_data_entry if entry includes it, otherwise throws an exception
+	const resource_data_entry& get_data_entry() const;
+
+	//Destructor
+	~resource_directory_entry();
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild resource directory
+
+	//Sets entry name
+	void set_name(const std::wstring& name);
+	//Sets entry ID
+	void set_id(uint32_t id);
+		
+	//Returns resource_directory if entry includes it, otherwise throws an exception
+	resource_directory& get_resource_directory();
+	//Returns resource_data_entry if entry includes it, otherwise throws an exception
+	resource_data_entry& get_data_entry();
+
+	//Adds resource_data_entry
+	void add_data_entry(const resource_data_entry& entry);
+	//Adds resource_directory
+	void add_resource_directory(const resource_directory& dir);
+
+private:
+	//Destroys included data
+	void release();
+
+private:
+	uint32_t id_;
+	std::wstring name_;
+
+	union includes
+	{
+		//Default constructor
+		includes();
+
+		//We use pointers, we're doing manual copying here
+		class resource_data_entry* data_;
+		class resource_directory* dir_; //We use pointer, because structs include each other
+	};
+
+	includes ptr_;
+
+	bool includes_data_, named_;
+};
+
+//Class representing resource directory
+class resource_directory
+{
+public:
+	typedef std::vector<resource_directory_entry> entry_list;
+
+public:
+	//Default constructor
+	resource_directory();
+	//Constructor from data
+	explicit resource_directory(const pe_win::image_resource_directory& dir);
+
+	//Returns characteristics of directory
+	uint32_t get_characteristics() const;
+	//Returns date and time stamp of directory
+	uint32_t get_timestamp() const;
+	//Returns number of named entries
+	uint32_t get_number_of_named_entries() const;
+	//Returns number of ID entries
+	uint32_t get_number_of_id_entries() const;
+	//Returns major version of directory
+	uint16_t get_major_version() const;
+	//Returns minor version of directory
+	uint16_t get_minor_version() const;
+	//Returns resource_directory_entry array
+	const entry_list& get_entry_list() const;
+	//Returns resource_directory_entry by ID. If not found - throws an exception
+	const resource_directory_entry& entry_by_id(uint32_t id) const;
+	//Returns resource_directory_entry by name. If not found - throws an exception
+	const resource_directory_entry& entry_by_name(const std::wstring& name) const;
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild resource directory
+
+	//Adds resource_directory_entry
+	void add_resource_directory_entry(const resource_directory_entry& entry);
+	//Clears resource_directory_entry array
+	void clear_resource_directory_entry_list();
+
+	//Sets characteristics of directory
+	void set_characteristics(uint32_t characteristics);
+	//Sets date and time stamp of directory
+	void set_timestamp(uint32_t timestamp);
+	//Sets number of named entries
+	void set_number_of_named_entries(uint32_t number);
+	//Sets number of ID entries
+	void set_number_of_id_entries(uint32_t number);
+	//Sets major version of directory
+	void set_major_version(uint16_t major_version);
+	//Sets minor version of directory
+	void get_minor_version(uint16_t minor_version);
+		
+	//Returns resource_directory_entry array
+	entry_list& get_entry_list();
+
+private:
+	uint32_t characteristics_;
+	uint32_t timestamp_;
+	uint16_t major_version_, minor_version_;
+	uint32_t number_of_named_entries_, number_of_id_entries_;
+	entry_list entries_;
+
+public: //Finder helpers
+	//Finds resource_directory_entry by ID
+	struct id_entry_finder
+	{
+	public:
+		explicit id_entry_finder(uint32_t id);
+		bool operator()(const resource_directory_entry& entry) const;
+
+	private:
+		uint32_t id_;
+	};
+
+	//Finds resource_directory_entry by name
+	struct name_entry_finder
+	{
+	public:
+		explicit name_entry_finder(const std::wstring& name);
+		bool operator()(const resource_directory_entry& entry) const;
+
+	private:
+		std::wstring name_;
+	};
+
+	//Finds resource_directory_entry by name or ID (universal)
+	struct entry_finder
+	{
+	public:
+		explicit entry_finder(const std::wstring& name);
+		explicit entry_finder(uint32_t id);
+		bool operator()(const resource_directory_entry& entry) const;
+
+	private:
+		std::wstring name_;
+		uint32_t id_;
+		bool named_;
+	};
+};
+
+//Returns resources (root resource_directory) from PE file
+const resource_directory get_resources(const pe_base& pe);
+
+//Resources rebuilder
+//resource_directory - root resource directory
+//resources_section - section where resource directory will be placed (must be attached to PE image)
+//resource_directory is non-constant, because it will be sorted
+//offset_from_section_start - offset from resources_section raw data start
+//save_to_pe_headers - if true, new resource directory information will be saved to PE image headers
+//auto_strip_last_section - if true and resources are placed in the last section, it will be automatically stripped
+//number_of_id_entries and number_of_named_entries for resource directories are recalculated and not used
+const image_directory rebuild_resources(pe_base& pe, resource_directory& info, section& resources_section, uint32_t offset_from_section_start = 0, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_rich_data.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_rich_data.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0497fa6469b68dd830e349e38537584ea9ef4d91
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_rich_data.cpp
@@ -0,0 +1,131 @@
+#include "pe_rich_data.h"
+
+namespace pe_bliss
+{
+//STUB OVERLAY
+//Default constructor
+rich_data::rich_data()
+	:number_(0), version_(0), times_(0)
+{}
+
+//Who knows, what these fields mean...
+uint32_t rich_data::get_number() const
+{
+	return number_;
+}
+
+uint32_t rich_data::get_version() const
+{
+	return version_;
+}
+
+uint32_t rich_data::get_times() const
+{
+	return times_;
+}
+
+void rich_data::set_number(uint32_t number)
+{
+	number_ = number;
+}
+
+void rich_data::set_version(uint32_t version)
+{
+	version_ = version;
+}
+
+void rich_data::set_times(uint32_t times)
+{
+	times_ = times;
+}
+
+//Returns MSVC rich data
+const rich_data_list get_rich_data(const pe_base& pe)
+{
+	//Returned value
+	rich_data_list ret;
+
+	const std::string& rich_overlay = pe.get_stub_overlay();
+
+	//If there's no rich overlay, return empty vector
+	if(rich_overlay.size() < sizeof(uint32_t))
+		return ret;
+
+	//True if rich data was found
+	bool found = false;
+
+	//Rich overlay ID ("Rich" word)
+	static const uint32_t rich_overlay_id = 0x68636952;
+
+	//Search for rich data overlay ID
+	const char* begin = &rich_overlay[0];
+	const char* end = begin + rich_overlay.length();
+	for(; begin != end; ++begin)
+	{
+		if(*reinterpret_cast<const uint32_t*>(begin) == rich_overlay_id)
+		{
+			found = true; //We've found it!
+			break;
+		}
+	}
+
+	//If we found it
+	if(found)
+	{
+		//Check remaining length
+		if(static_cast<size_t>(end - begin) < sizeof(uint32_t))
+			return ret;
+
+		//The XOR key is after "Rich" word, we should get it
+		uint32_t xorkey = *reinterpret_cast<const uint32_t*>(begin + sizeof(uint32_t));
+
+		//True if rich data was found
+		found = false;
+
+		//Second search for signature "DanS"
+		begin = &rich_overlay[0];
+		for(; begin != end; ++begin)
+		{
+			if((*reinterpret_cast<const uint32_t*>(begin) ^ xorkey) == 0x536e6144) //"DanS"
+			{
+				found = true;
+				break;
+			}
+		}
+
+		//If second signature is found
+		if(found)
+		{
+			begin += sizeof(uint32_t) * 3;
+			//List all rich data structures
+			while(begin < end)
+			{
+				begin += sizeof(uint32_t);
+				if(begin >= end)
+					break;
+
+				//Check for rich overlay data end ("Rich" word reached)
+				if(*reinterpret_cast<const uint32_t*>(begin) == rich_overlay_id)
+					break;
+
+				//Create rich_data structure
+				rich_data data;
+				data.set_number((*reinterpret_cast<const uint32_t*>(begin) ^ xorkey) >> 16);
+				data.set_version((*reinterpret_cast<const uint32_t*>(begin) ^ xorkey) & 0xFFFF);
+
+				begin += sizeof(uint32_t);
+				if(begin >= end)
+					break;
+
+				data.set_times(*reinterpret_cast<const uint32_t*>(begin) ^ xorkey);
+
+				//Save rich data structure
+				ret.push_back(data);
+			}
+		}
+	}
+
+	//Return rich data structures list
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_rich_data.h b/irdb-lib/pebliss/trunk/pe_lib/pe_rich_data.h
new file mode 100644
index 0000000000000000000000000000000000000000..a5689453152e368ee8b411c075e220f84827661f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_rich_data.h
@@ -0,0 +1,40 @@
+#ifndef pebliss_pe_rich_data_h
+#define pebliss_pe_rich_data_h
+#pragma once
+#include <vector>
+#include "pe_structures.h"
+#include "pe_base.h"
+
+namespace pe_bliss
+{
+//Rich data overlay class of Microsoft Visual Studio
+class rich_data
+{
+public:
+	//Default constructor
+	rich_data();
+
+public: //Getters
+	//Who knows, what these fields mean...
+	uint32_t get_number() const;
+	uint32_t get_version() const;
+	uint32_t get_times() const;
+
+public: //Setters, used by PE library only
+	void set_number(uint32_t number);
+	void set_version(uint32_t version);
+	void set_times(uint32_t times);
+
+private:
+	uint32_t number_;
+	uint32_t version_;
+	uint32_t times_;
+};
+
+//Rich data list typedef
+typedef std::vector<rich_data> rich_data_list;
+
+//Returns a vector with rich data (stub overlay)
+const rich_data_list get_rich_data(const pe_base& pe);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_section.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_section.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e7def185cb6910f98cd78216ac891c2c750627ea
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_section.cpp
@@ -0,0 +1,281 @@
+#include <string.h>
+#include "utils.h"
+#include "pe_section.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Section structure default constructor
+section::section()
+	:old_size_(static_cast<size_t>(-1))
+{
+	memset(&header_, 0, sizeof(image_section_header));
+}
+
+//Sets the name of section (8 characters maximum)
+void section::set_name(const std::string& name)
+{
+	memset(header_.Name, 0, sizeof(header_.Name));
+	memcpy(header_.Name, name.c_str(), std::min<size_t>(name.length(), sizeof(header_.Name)));
+}
+
+//Returns section name
+const std::string section::get_name() const
+{
+	char buf[9] = {0};
+	memcpy(buf, header_.Name, 8);
+	return std::string(buf);
+}
+
+//Set flag (attribute) of section
+section& section::set_flag(uint32_t flag, bool setflag)
+{
+	if(setflag)
+		header_.Characteristics |= flag;
+	else
+		header_.Characteristics &= ~flag;
+
+	return *this;
+}
+
+//Sets "readable" attribute of section
+section& section::readable(bool readable)
+{
+	return set_flag(image_scn_mem_read, readable);
+}
+
+//Sets "writeable" attribute of section
+section& section::writeable(bool writeable)
+{
+	return set_flag(image_scn_mem_write, writeable);
+}
+
+//Sets "executable" attribute of section
+section& section::executable(bool executable)
+{
+	return set_flag(image_scn_mem_execute, executable);
+}
+
+//Sets "shared" attribute of section
+section& section::shared(bool shared)
+{
+	return set_flag(image_scn_mem_shared, shared);
+}
+
+//Sets "discardable" attribute of section
+section& section::discardable(bool discardable)
+{
+	return set_flag(image_scn_mem_discardable, discardable);
+}
+
+//Returns true if section is readable
+bool section::readable() const
+{
+	return (header_.Characteristics & image_scn_mem_read) != 0;
+}
+
+//Returns true if section is writeable
+bool section::writeable() const
+{
+	return (header_.Characteristics & image_scn_mem_write) != 0;
+}
+
+//Returns true if section is executable
+bool section::executable() const
+{
+	return (header_.Characteristics & image_scn_mem_execute) != 0;
+}
+
+bool section::shared() const
+{
+	return (header_.Characteristics & image_scn_mem_shared) != 0;
+}
+
+bool section::discardable() const
+{
+	return (header_.Characteristics & image_scn_mem_discardable) != 0;
+}
+
+//Returns true if section has no RAW data
+bool section::empty() const
+{
+	if(old_size_ != static_cast<size_t>(-1)) //If virtual memory is mapped, check raw data length (old_size_)
+		return old_size_ == 0;
+	else
+		return raw_data_.empty();
+}
+
+//Returns raw section data from file image
+std::string& section::get_raw_data()
+{
+	unmap_virtual();
+	return raw_data_;
+}
+
+//Sets raw section data from file image
+void section::set_raw_data(const std::string& data)
+{
+	old_size_ = static_cast<size_t>(-1);
+	raw_data_ = data;
+}
+
+//Returns raw section data from file image
+const std::string& section::get_raw_data() const
+{
+	unmap_virtual();
+	return raw_data_;
+}
+
+//Returns mapped virtual section data
+const std::string& section::get_virtual_data(uint32_t section_alignment) const
+{
+	map_virtual(section_alignment);
+	return raw_data_;
+}
+
+//Returns mapped virtual section data
+std::string& section::get_virtual_data(uint32_t section_alignment)
+{
+	map_virtual(section_alignment);
+	return raw_data_;
+}
+
+//Maps virtual section data
+void section::map_virtual(uint32_t section_alignment) const
+{
+	uint32_t aligned_virtual_size = get_aligned_virtual_size(section_alignment);
+	if(old_size_ == static_cast<size_t>(-1) && aligned_virtual_size && aligned_virtual_size > raw_data_.length())
+	{
+		old_size_ = raw_data_.length();
+		raw_data_.resize(aligned_virtual_size, 0);
+	}
+}
+
+//Unmaps virtual section data
+void section::unmap_virtual() const
+{
+	if(old_size_ != static_cast<size_t>(-1))
+	{
+		raw_data_.resize(old_size_, 0);
+		old_size_ = static_cast<size_t>(-1);
+	}
+}
+
+//Returns section virtual size
+uint32_t section::get_virtual_size() const
+{
+	return header_.Misc.VirtualSize;
+}
+
+//Returns section virtual address
+uint32_t section::get_virtual_address() const
+{
+	return header_.VirtualAddress;
+}
+
+//Returns size of section raw data
+uint32_t section::get_size_of_raw_data() const
+{
+	return header_.SizeOfRawData;
+}
+
+//Returns pointer to raw section data in PE file
+uint32_t section::get_pointer_to_raw_data() const
+{
+	return header_.PointerToRawData;
+}
+
+//Returns section characteristics
+uint32_t section::get_characteristics() const
+{
+	return header_.Characteristics;
+}
+
+//Returns raw image section header
+const pe_win::image_section_header& section::get_raw_header() const
+{
+	return header_;
+}
+
+//Returns raw image section header
+pe_win::image_section_header& section::get_raw_header()
+{
+	return header_;
+}
+
+//Calculates aligned virtual section size
+uint32_t section::get_aligned_virtual_size(uint32_t section_alignment) const
+{
+	if(get_size_of_raw_data())
+	{
+		if(!get_virtual_size())
+		{
+			//If section virtual size is zero
+			//Set aligned virtual size of section as aligned raw size
+			return pe_utils::align_up(get_size_of_raw_data(), section_alignment);
+		}
+	}
+
+	return pe_utils::align_up(get_virtual_size(), section_alignment);
+}
+
+//Calculates aligned raw section size
+uint32_t section::get_aligned_raw_size(uint32_t file_alignment) const
+{
+	if(get_size_of_raw_data())
+		return pe_utils::align_up(get_size_of_raw_data(), file_alignment);
+	else
+		return 0;
+}
+
+//Sets size of raw section data
+void section::set_size_of_raw_data(uint32_t size_of_raw_data)
+{
+	header_.SizeOfRawData = size_of_raw_data;
+}
+
+//Sets pointer to section raw data
+void section::set_pointer_to_raw_data(uint32_t pointer_to_raw_data)
+{
+	header_.PointerToRawData = pointer_to_raw_data;
+}
+
+//Sets section characteristics
+void section::set_characteristics(uint32_t characteristics)
+{
+	header_.Characteristics = characteristics;
+}
+
+//Sets section virtual size
+void section::set_virtual_size(uint32_t virtual_size)
+{
+	header_.Misc.VirtualSize = virtual_size;
+}
+
+//Sets section virtual address
+void section::set_virtual_address(uint32_t virtual_address)
+{
+	header_.VirtualAddress = virtual_address;
+}
+
+//Section by file offset finder helper (4gb max)
+section_by_raw_offset::section_by_raw_offset(uint32_t offset)
+	:offset_(offset)
+{}
+
+bool section_by_raw_offset::operator()(const section& s) const
+{
+	return (s.get_pointer_to_raw_data() <= offset_)
+		&& (s.get_pointer_to_raw_data() + s.get_size_of_raw_data() > offset_);
+}
+
+section_ptr_finder::section_ptr_finder(const section& s)
+	:s_(s)
+{}
+
+bool section_ptr_finder::operator()(const section& s) const
+{
+	return &s == &s_;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_section.h b/irdb-lib/pebliss/trunk/pe_lib/pe_section.h
new file mode 100644
index 0000000000000000000000000000000000000000..552959c6833da6716610d801a7e33bd00e2fbd95
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_section.h
@@ -0,0 +1,144 @@
+#ifndef pebliss_pe_section_h
+#define pebliss_pe_section_h
+#pragma once
+#ifndef pebliss_section_h
+#define pebliss_section_h
+
+#include <string>
+#include <vector>
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+//Enumeration of section data types, used in functions below
+enum section_data_type
+{
+	section_data_raw,
+	section_data_virtual
+};
+
+//Class representing image section
+class section
+{
+public:
+	//Default constructor
+	section();
+
+	//Sets the name of section (stripped to 8 characters)
+	void set_name(const std::string& name);
+
+	//Returns the name of section
+	const std::string get_name() const;
+
+	//Changes attributes of section
+	section& readable(bool readable);
+	section& writeable(bool writeable);
+	section& executable(bool executable);
+	section& shared(bool shared);
+	section& discardable(bool discardable);
+
+	//Returns attributes of section
+	bool readable() const;
+	bool writeable() const;
+	bool executable() const;
+	bool shared() const;
+	bool discardable() const;
+
+	//Returns true if section has no RAW data
+	bool empty() const;
+
+	//Returns raw section data from file image
+	std::string& get_raw_data();
+	//Returns raw section data from file image
+	const std::string& get_raw_data() const;
+	//Returns mapped virtual section data
+	const std::string& get_virtual_data(uint32_t section_alignment) const;
+	//Returns mapped virtual section data
+	std::string& get_virtual_data(uint32_t section_alignment);
+
+public: //Header getters
+	//Returns section virtual size
+	uint32_t get_virtual_size() const;
+	//Returns section virtual address (RVA)
+	uint32_t get_virtual_address() const;
+	//Returns size of section raw data
+	uint32_t get_size_of_raw_data() const;
+	//Returns pointer to raw section data in PE file
+	uint32_t get_pointer_to_raw_data() const;
+	//Returns section characteristics
+	uint32_t get_characteristics() const;
+
+	//Returns raw image section header
+	const pe_win::image_section_header& get_raw_header() const;
+
+public: //Aligned sizes calculation
+	//Calculates aligned virtual section size
+	uint32_t get_aligned_virtual_size(uint32_t section_alignment) const;
+	//Calculates aligned raw section size
+	uint32_t get_aligned_raw_size(uint32_t file_alignment) const;
+
+public: //Setters
+	//Sets size of raw section data
+	void set_size_of_raw_data(uint32_t size_of_raw_data);
+	//Sets pointer to section raw data
+	void set_pointer_to_raw_data(uint32_t pointer_to_raw_data);
+	//Sets section characteristics
+	void set_characteristics(uint32_t characteristics);
+	//Sets raw section data from file image
+	void set_raw_data(const std::string& data);
+
+public: //Setters, be careful
+	//Sets section virtual size (doesn't set internal aligned virtual size, changes only header value)
+	//Better use pe_base::set_section_virtual_size
+	void set_virtual_size(uint32_t virtual_size);
+	//Sets section virtual address
+	void set_virtual_address(uint32_t virtual_address);
+	//Returns raw image section header
+	pe_win::image_section_header& get_raw_header();
+
+private:
+	//Section header
+	pe_win::image_section_header header_;
+
+	//Maps virtual section data
+	void map_virtual(uint32_t section_alignment) const;
+
+	//Unmaps virtual section data
+	void unmap_virtual() const;
+
+	//Set flag (attribute) of section
+	section& set_flag(uint32_t flag, bool setflag);
+
+	//Old size of section (stored after mapping of virtual section memory)
+	mutable std::size_t old_size_;
+
+	//Section raw/virtual data
+	mutable std::string raw_data_;
+};
+
+//Section by file offset finder helper (4gb max)
+struct section_by_raw_offset
+{
+public:
+	explicit section_by_raw_offset(uint32_t offset);
+	bool operator()(const section& s) const;
+
+private:
+	uint32_t offset_;
+};
+
+//Helper: finder of section* in sections list
+struct section_ptr_finder
+{
+public:
+	explicit section_ptr_finder(const section& s);
+	bool operator()(const section& s) const;
+
+private:
+	const section& s_;
+};
+
+typedef std::vector<section> section_list;
+}
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_structures.h b/irdb-lib/pebliss/trunk/pe_lib/pe_structures.h
new file mode 100644
index 0000000000000000000000000000000000000000..0487d02683af92f4509641336028f444e9933ab7
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_structures.h
@@ -0,0 +1,1030 @@
+#ifndef pebliss_pe_structures_h
+#define pebliss_pe_structures_h
+#pragma once
+#ifndef pe_struct_h
+#define pe_struct_h
+
+#include <string>
+#include <sstream>
+#include "stdint_defs.h"
+#if defined(_MSC_VER)
+#define PE_BLISS_WINDOWS
+#endif
+
+namespace pe_bliss
+{
+//Enumeration of PE types
+enum pe_type
+{
+	pe_type_32,
+	pe_type_64
+};
+
+namespace pe_win
+{
+const uint32_t image_numberof_directory_entries = 16;
+const uint32_t image_nt_optional_hdr32_magic = 0x10b;
+const uint32_t image_nt_optional_hdr64_magic = 0x20b;
+const uint32_t image_resource_name_is_string = 0x80000000;
+const uint32_t image_resource_data_is_directory = 0x80000000;
+
+const uint32_t image_dllcharacteristics_dynamic_base = 0x0040;     // DLL can move.
+const uint32_t image_dllcharacteristics_force_integrity = 0x0080;     // Code Integrity Image
+const uint32_t image_dllcharacteristics_nx_compat = 0x0100;     // Image is NX compatible
+const uint32_t image_dllcharacteristics_no_isolation = 0x0200;     // Image understands isolation and doesn't want it
+const uint32_t image_dllcharacteristics_no_seh = 0x0400;     // Image does not use SEH.  No SE handler may reside in this image
+const uint32_t image_dllcharacteristics_no_bind = 0x0800;     // Do not bind this image.
+const uint32_t image_dllcharacteristics_wdm_driver = 0x2000;     // Driver uses WDM model
+const uint32_t image_dllcharacteristics_terminal_server_aware = 0x8000;
+
+const uint32_t image_sizeof_file_header = 20;
+
+const uint32_t image_file_relocs_stripped = 0x0001;  // Relocation info stripped from file.
+const uint32_t image_file_executable_image = 0x0002;  // File is executable  (i.e. no unresolved externel references).
+const uint32_t image_file_line_nums_stripped = 0x0004;  // Line nunbers stripped from file.
+const uint32_t image_file_local_syms_stripped = 0x0008;  // Local symbols stripped from file.
+const uint32_t image_file_aggresive_ws_trim = 0x0010;  // Agressively trim working set
+const uint32_t image_file_large_address_aware = 0x0020;  // App can handle >2gb addresses
+const uint32_t image_file_bytes_reversed_lo = 0x0080;  // Bytes of machine word are reversed.
+const uint32_t image_file_32bit_machine = 0x0100;  // 32 bit word machine.
+const uint32_t image_file_debug_stripped = 0x0200;  // Debugging info stripped from file in .DBG file
+const uint32_t image_file_removable_run_from_swap = 0x0400;  // If Image is on removable media, copy and run from the swap file.
+const uint32_t image_file_net_run_from_swap = 0x0800;  // If Image is on Net, copy and run from the swap file.
+const uint32_t image_file_system = 0x1000;  // System File.
+const uint32_t image_file_dll = 0x2000;  // File is a DLL.
+const uint32_t image_file_up_system_only = 0x4000;  // File should only be run on a UP machine
+const uint32_t image_file_bytes_reversed_hi = 0x8000;  // Bytes of machine word are reversed.
+
+const uint32_t image_scn_lnk_nreloc_ovfl = 0x01000000;  // Section contains extended relocations.
+const uint32_t image_scn_mem_discardable = 0x02000000;  // Section can be discarded.
+const uint32_t image_scn_mem_not_cached = 0x04000000;  // Section is not cachable.
+const uint32_t image_scn_mem_not_paged = 0x08000000;  // Section is not pageable.
+const uint32_t image_scn_mem_shared = 0x10000000;  // Section is shareable.
+const uint32_t image_scn_mem_execute = 0x20000000;  // Section is executable.
+const uint32_t image_scn_mem_read = 0x40000000;  // Section is readable.
+const uint32_t image_scn_mem_write = 0x80000000;  // Section is writeable.
+
+const uint32_t image_scn_cnt_code = 0x00000020;  // Section contains code.
+const uint32_t image_scn_cnt_initialized_data = 0x00000040;  // Section contains initialized data.
+const uint32_t image_scn_cnt_uninitialized_data = 0x00000080;  // Section contains uninitialized data.
+
+//Directory Entries
+const uint32_t image_directory_entry_export = 0;   // Export Directory
+const uint32_t image_directory_entry_import = 1;   // Import Directory
+const uint32_t image_directory_entry_resource = 2;   // Resource Directory
+const uint32_t image_directory_entry_exception = 3;   // Exception Directory
+const uint32_t image_directory_entry_security = 4;   // Security Directory
+const uint32_t image_directory_entry_basereloc = 5;   // Base Relocation Table
+const uint32_t image_directory_entry_debug = 6;   // Debug Directory
+const uint32_t image_directory_entry_architecture = 7;   // Architecture Specific Data
+const uint32_t image_directory_entry_globalptr = 8;   // RVA of GP
+const uint32_t image_directory_entry_tls = 9;   // TLS Directory
+const uint32_t image_directory_entry_load_config = 10;   // Load Configuration Directory
+const uint32_t image_directory_entry_bound_import = 11;   // Bound Import Directory in headers
+const uint32_t image_directory_entry_iat = 12;   // Import Address Table
+const uint32_t image_directory_entry_delay_import = 13;   // Delay Load Import Descriptors
+const uint32_t image_directory_entry_com_descriptor = 14;   // COM Runtime descriptor
+
+//Subsystem Values
+const uint32_t image_subsystem_unknown = 0;   // Unknown subsystem.
+const uint32_t image_subsystem_native = 1;   // Image doesn't require a subsystem.
+const uint32_t image_subsystem_windows_gui = 2;   // Image runs in the Windows GUI subsystem.
+const uint32_t image_subsystem_windows_cui = 3;   // Image runs in the Windows character subsystem.
+const uint32_t image_subsystem_os2_cui = 5;   // image runs in the OS/2 character subsystem.
+const uint32_t image_subsystem_posix_cui = 7;   // image runs in the Posix character subsystem.
+const uint32_t image_subsystem_native_windows = 8;   // image is a native Win9x driver.
+const uint32_t image_subsystem_windows_ce_gui = 9;   // Image runs in the Windows CE subsystem.
+const uint32_t image_subsystem_efi_application = 10;  //
+const uint32_t image_subsystem_efi_boot_service_driver = 11;   //
+const uint32_t image_subsystem_efi_runtime_driver = 12;  //
+const uint32_t image_subsystem_efi_rom = 13;
+const uint32_t image_subsystem_xbox = 14;
+const uint32_t image_subsystem_windows_boot_application = 16;
+
+//Imports
+const uint64_t image_ordinal_flag64 = 0x8000000000000000ull;
+const uint32_t image_ordinal_flag32 = 0x80000000;
+
+//Based relocation types
+const uint32_t image_rel_based_absolute = 0;
+const uint32_t image_rel_based_high =  1;
+const uint32_t image_rel_based_low = 2;
+const uint32_t image_rel_based_highlow = 3;
+const uint32_t image_rel_based_highadj = 4;
+const uint32_t image_rel_based_mips_jmpaddr = 5;
+const uint32_t image_rel_based_mips_jmpaddr16 = 9;
+const uint32_t image_rel_based_ia64_imm64 = 9;
+const uint32_t image_rel_based_dir64 = 10;
+
+//Exception directory
+//The function has an exception handler that should be called when looking for functions that need to examine exceptions
+const uint32_t unw_flag_ehandler = 0x01;
+//The function has a termination handler that should be called when unwinding an exception
+const uint32_t unw_flag_uhandler = 0x02;
+//This unwind info structure is not the primary one for the procedure.
+//Instead, the chained unwind info entry is the contents of a previous RUNTIME_FUNCTION entry.
+//If this flag is set, then the UNW_FLAG_EHANDLER and UNW_FLAG_UHANDLER flags must be cleared.
+//Also, the frame register and fixed-stack allocation fields must have the same values as in the primary unwind info
+const uint32_t unw_flag_chaininfo = 0x04;
+
+//Debug
+const uint32_t image_debug_misc_exename = 1;
+const uint32_t image_debug_type_unknown = 0;
+const uint32_t image_debug_type_coff = 1;
+const uint32_t image_debug_type_codeview = 2;
+const uint32_t image_debug_type_fpo = 3;
+const uint32_t image_debug_type_misc = 4;
+const uint32_t image_debug_type_exception = 5;
+const uint32_t image_debug_type_fixup = 6;
+const uint32_t image_debug_type_omap_to_src = 7;
+const uint32_t image_debug_type_omap_from_src = 8;
+const uint32_t image_debug_type_borland = 9;
+const uint32_t image_debug_type_reserved10 = 10;
+const uint32_t image_debug_type_clsid = 11;
+
+
+//Storage classes
+const uint32_t image_sym_class_end_of_function = static_cast<uint8_t>(-1);
+const uint32_t image_sym_class_null = 0x0000;
+const uint32_t image_sym_class_automatic = 0x0001;
+const uint32_t image_sym_class_external = 0x0002;
+const uint32_t image_sym_class_static = 0x0003;
+const uint32_t image_sym_class_register = 0x0004;
+const uint32_t image_sym_class_external_def = 0x0005;
+const uint32_t image_sym_class_label = 0x0006;
+const uint32_t image_sym_class_undefined_label = 0x0007;
+const uint32_t image_sym_class_member_of_struct = 0x0008;
+const uint32_t image_sym_class_argument = 0x0009;
+const uint32_t image_sym_class_struct_tag = 0x000a;
+const uint32_t image_sym_class_member_of_union = 0x000b;
+const uint32_t image_sym_class_union_tag = 0x000c;
+const uint32_t image_sym_class_type_definition = 0x000d;
+const uint32_t image_sym_class_undefined_static = 0x000e;
+const uint32_t image_sym_class_enum_tag = 0x000f;
+const uint32_t image_sym_class_member_of_enum = 0x0010;
+const uint32_t image_sym_class_register_param = 0x0011;
+const uint32_t image_sym_class_bit_field = 0x0012;
+
+const uint32_t image_sym_class_far_external = 0x0044;
+
+const uint32_t image_sym_class_block = 0x0064;
+const uint32_t image_sym_class_function = 0x0065;
+const uint32_t image_sym_class_end_of_struct = 0x0066;
+const uint32_t image_sym_class_file = 0x0067;
+
+const uint32_t image_sym_class_section = 0x0068;
+const uint32_t image_sym_class_weak_external = 0x0069;
+
+const uint32_t image_sym_class_clr_token = 0x006b;
+
+//type packing constants
+const uint32_t n_btmask = 0x000f;
+const uint32_t n_tmask = 0x0030;
+const uint32_t n_tmask1 = 0x00c0;
+const uint32_t n_tmask2 = 0x00f0;
+const uint32_t n_btshft = 4;
+const uint32_t n_tshift = 2;
+
+//Type (derived) values.
+const uint32_t image_sym_dtype_null = 0;          // no derived type.
+const uint32_t image_sym_dtype_pointer = 1;       // pointer.
+const uint32_t image_sym_dtype_function = 2;      // function.
+const uint32_t image_sym_dtype_array = 3;         // array.
+
+// Is x a function?
+//TODO
+#ifndef ISFCN
+#define ISFCN(x) (((x) & n_tmask) == (image_sym_dtype_function << n_btshft))
+#endif
+
+//Version info
+const uint32_t vs_ffi_fileflagsmask = 0x0000003FL;
+
+const uint32_t vs_ffi_signature = 0xFEEF04BDL;
+const uint32_t vs_ffi_strucversion = 0x00010000L;
+
+/* ----- VS_VERSION.dwFileFlags ----- */
+const uint32_t vs_ff_debug = 0x00000001L;
+const uint32_t vs_ff_prerelease = 0x00000002L;
+const uint32_t vs_ff_patched = 0x00000004L;
+const uint32_t vs_ff_privatebuild = 0x00000008L;
+const uint32_t vs_ff_infoinferred = 0x00000010L;
+const uint32_t vs_ff_specialbuild = 0x00000020L;
+
+/* ----- VS_VERSION.dwFileOS ----- */
+const uint32_t vos_unknown = 0x00000000L;
+const uint32_t vos_dos = 0x00010000L;
+const uint32_t vos_os216 = 0x00020000L;
+const uint32_t vos_os232 = 0x00030000L;
+const uint32_t vos_nt = 0x00040000L;
+const uint32_t vos_wince = 0x00050000L;
+
+const uint32_t vos__base = 0x00000000L;
+const uint32_t vos__windows16 = 0x00000001L;
+const uint32_t vos__pm16 = 0x00000002L;
+const uint32_t vos__pm32 = 0x00000003L;
+const uint32_t vos__windows32 = 0x00000004L;
+
+const uint32_t vos_dos_windows16 = 0x00010001L;
+const uint32_t vos_dos_windows32 = 0x00010004L;
+const uint32_t vos_os216_pm16 = 0x00020002L;
+const uint32_t vos_os232_pm32 = 0x00030003L;
+const uint32_t vos_nt_windows32 = 0x00040004L;
+
+/* ----- VS_VERSION.dwFileType ----- */
+const uint32_t vft_unknown = 0x00000000L;
+const uint32_t vft_app = 0x00000001L;
+const uint32_t vft_dll = 0x00000002L;
+const uint32_t vft_drv = 0x00000003L;
+const uint32_t vft_font =  0x00000004L;
+const uint32_t vft_vxd = 0x00000005L;
+const uint32_t vft_static_lib = 0x00000007L;
+
+const uint32_t message_resource_unicode = 0x0001;
+
+#ifndef SOLARIS
+#pragma pack(push, 1)
+#endif
+
+//Windows GUID structure
+struct guid
+{
+	uint32_t Data1;
+	uint16_t Data2;
+	uint16_t Data3;
+	uint8_t Data4[8];
+};
+
+//DOS .EXE header
+struct image_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
+};
+
+//Directory format
+struct image_data_directory
+{
+	uint32_t VirtualAddress;
+	uint32_t Size;
+};
+
+//Optional header format
+struct image_optional_header32
+{
+	//Standard fields
+	uint16_t Magic;
+	uint8_t  MajorLinkerVersion;
+	uint8_t  MinorLinkerVersion;
+	uint32_t SizeOfCode;
+	uint32_t SizeOfInitializedData;
+	uint32_t SizeOfUninitializedData;
+	uint32_t AddressOfEntryPoint;
+	uint32_t BaseOfCode;
+	uint32_t BaseOfData;
+
+	//NT additional fields
+	uint32_t ImageBase;
+	uint32_t SectionAlignment;
+	uint32_t FileAlignment;
+	uint16_t MajorOperatingSystemVersion;
+	uint16_t MinorOperatingSystemVersion;
+	uint16_t MajorImageVersion;
+	uint16_t MinorImageVersion;
+	uint16_t MajorSubsystemVersion;
+	uint16_t MinorSubsystemVersion;
+	uint32_t Win32VersionValue;
+	uint32_t SizeOfImage;
+	uint32_t SizeOfHeaders;
+	uint32_t CheckSum;
+	uint16_t Subsystem;
+	uint16_t DllCharacteristics;
+	uint32_t SizeOfStackReserve;
+	uint32_t SizeOfStackCommit;
+	uint32_t SizeOfHeapReserve;
+	uint32_t SizeOfHeapCommit;
+	uint32_t LoaderFlags;
+	uint32_t NumberOfRvaAndSizes;
+	image_data_directory DataDirectory[image_numberof_directory_entries];
+};
+
+struct image_optional_header64
+{
+	uint16_t Magic;
+	uint8_t  MajorLinkerVersion;
+	uint8_t  MinorLinkerVersion;
+	uint32_t SizeOfCode;
+	uint32_t SizeOfInitializedData;
+	uint32_t SizeOfUninitializedData;
+	uint32_t AddressOfEntryPoint;
+	uint32_t BaseOfCode;
+	uint64_t ImageBase;
+	uint32_t SectionAlignment;
+	uint32_t FileAlignment;
+	uint16_t MajorOperatingSystemVersion;
+	uint16_t MinorOperatingSystemVersion;
+	uint16_t MajorImageVersion;
+	uint16_t MinorImageVersion;
+	uint16_t MajorSubsystemVersion;
+	uint16_t MinorSubsystemVersion;
+	uint32_t Win32VersionValue;
+	uint32_t SizeOfImage;
+	uint32_t SizeOfHeaders;
+	uint32_t CheckSum;
+	uint16_t Subsystem;
+	uint16_t DllCharacteristics;
+	uint64_t SizeOfStackReserve;
+	uint64_t SizeOfStackCommit;
+	uint64_t SizeOfHeapReserve;
+	uint64_t SizeOfHeapCommit;
+	uint32_t LoaderFlags;
+	uint32_t NumberOfRvaAndSizes;
+	image_data_directory DataDirectory[image_numberof_directory_entries];
+};
+
+struct image_file_header
+{
+	uint16_t Machine;
+	uint16_t NumberOfSections;
+	uint32_t TimeDateStamp;
+	uint32_t PointerToSymbolTable;
+	uint32_t NumberOfSymbols;
+	uint16_t SizeOfOptionalHeader;
+	uint16_t Characteristics;
+};
+
+struct image_nt_headers64
+{
+	uint32_t Signature;
+	image_file_header FileHeader;
+	image_optional_header64 OptionalHeader;
+};
+
+struct image_nt_headers32
+{
+	uint32_t Signature;
+	image_file_header FileHeader;
+	image_optional_header32 OptionalHeader;
+};
+
+//Section header format
+struct image_section_header
+{
+	uint8_t Name[8];
+	union
+	{
+		uint32_t PhysicalAddress;
+		uint32_t VirtualSize;
+	} Misc;
+
+	uint32_t VirtualAddress;
+	uint32_t SizeOfRawData;
+	uint32_t PointerToRawData;
+	uint32_t PointerToRelocations;
+	uint32_t PointerToLinenumbers;
+	uint16_t NumberOfRelocations;
+	uint16_t NumberOfLinenumbers;
+	uint32_t Characteristics;
+};
+
+
+/// RESOURCES ///
+struct image_resource_directory
+{
+	uint32_t Characteristics;
+	uint32_t TimeDateStamp;
+	uint16_t MajorVersion;
+	uint16_t MinorVersion;
+	uint16_t NumberOfNamedEntries;
+	uint16_t NumberOfIdEntries;
+	//  IMAGE_RESOURCE_DIRECTORY_ENTRY DirectoryEntries[];
+};
+
+struct vs_fixedfileinfo
+{
+	uint32_t dwSignature;            /* e.g. 0xfeef04bd */
+	uint32_t dwStrucVersion;         /* e.g. 0x00000042 = "0.42" */
+	uint32_t dwFileVersionMS;        /* e.g. 0x00030075 = "3.75" */
+	uint32_t dwFileVersionLS;        /* e.g. 0x00000031 = "0.31" */
+	uint32_t dwProductVersionMS;     /* e.g. 0x00030010 = "3.10" */
+	uint32_t dwProductVersionLS;     /* e.g. 0x00000031 = "0.31" */
+	uint32_t dwFileFlagsMask;        /* = 0x3F for version "0.42" */
+	uint32_t dwFileFlags;            /* e.g. VFF_DEBUG | VFF_PRERELEASE */
+	uint32_t dwFileOS;               /* e.g. VOS_DOS_WINDOWS16 */
+	uint32_t dwFileType;             /* e.g. VFT_DRIVER */
+	uint32_t dwFileSubtype;          /* e.g. VFT2_DRV_KEYBOARD */
+	uint32_t dwFileDateMS;           /* e.g. 0 */
+	uint32_t dwFileDateLS;           /* e.g. 0 */
+};
+
+struct bitmapinfoheader
+{
+	uint32_t biSize;
+	int32_t  biWidth;
+	int32_t  biHeight;
+	uint16_t biPlanes;
+	uint16_t biBitCount;
+	uint32_t biCompression;
+	uint32_t biSizeImage;
+	int32_t  biXPelsPerMeter;
+	int32_t  biYPelsPerMeter;
+	uint32_t biClrUsed;
+	uint32_t biClrImportant;
+};
+
+struct message_resource_entry
+{
+	uint16_t Length;
+	uint16_t Flags;
+	uint8_t  Text[1];
+};
+
+struct message_resource_block
+{
+	uint32_t LowId;
+	uint32_t HighId;
+	uint32_t OffsetToEntries;
+};
+
+struct message_resource_data
+{
+	uint32_t NumberOfBlocks;
+	message_resource_block Blocks[1];
+};
+
+struct image_resource_directory_entry
+{
+	union
+	{
+		struct
+		{
+			uint32_t NameOffset:31;
+			uint32_t NameIsString:1;
+		};
+		uint32_t Name;
+		uint16_t Id;
+	};
+
+	union
+	{
+		uint32_t OffsetToData;
+		struct
+		{
+			uint32_t OffsetToDirectory:31;
+			uint32_t DataIsDirectory:1;
+		};
+	};
+};
+
+struct image_resource_data_entry
+{
+	uint32_t OffsetToData;
+	uint32_t Size;
+	uint32_t CodePage;
+	uint32_t Reserved;
+};
+
+#ifndef SOLARIS
+#pragma pack(push, 2)
+#endif
+struct bitmapfileheader
+{
+	uint16_t bfType;
+	uint32_t bfSize;
+	uint16_t bfReserved1;
+	uint16_t bfReserved2;
+	uint32_t bfOffBits;
+};
+#ifndef SOLARIS
+#pragma pack(pop)
+#endif
+
+
+
+//Structure representing ICON file header
+struct ico_header
+{
+	uint16_t Reserved;
+	uint16_t Type; //1
+	uint16_t Count; //Count of icons included in icon group
+};
+
+//Structure that is stored in icon group directory in PE resources
+struct icon_group
+{
+	uint8_t Width;
+	uint8_t Height;
+	uint8_t ColorCount;
+	uint8_t Reserved;
+	uint16_t Planes;
+	uint16_t BitCount;
+	uint32_t SizeInBytes;
+	uint16_t Number; //Represents resource ID in PE icon list
+};
+
+//Structure representing ICON directory entry inside ICON file
+struct icondirentry
+{
+	uint8_t Width;
+	uint8_t Height;
+	uint8_t ColorCount;
+	uint8_t Reserved;
+	uint16_t Planes;
+	uint16_t BitCount;
+	uint32_t SizeInBytes;
+	uint32_t ImageOffset; //Offset from start of header to the image
+};
+
+//Structure representing CURSOR file header
+struct cursor_header
+{
+	uint16_t Reserved;
+	uint16_t Type; //2
+	uint16_t Count; //Count of cursors included in cursor group
+};
+
+struct cursor_group
+{
+	uint16_t Width;
+	uint16_t Height; //Divide by 2 to get the actual height.
+	uint16_t Planes;
+	uint16_t BitCount;
+	uint32_t SizeInBytes;
+	uint16_t Number; //Represents resource ID in PE icon list
+};
+
+//Structure representing CURSOR directory entry inside CURSOR file
+struct cursordirentry
+{
+	uint8_t Width; //Set to CURSOR_GROUP::Height/2.
+	uint8_t Height;
+	uint8_t ColorCount;
+	uint8_t Reserved;
+	uint16_t HotspotX;
+	uint16_t HotspotY;
+	uint32_t SizeInBytes;
+	uint32_t ImageOffset; //Offset from start of header to the image
+};
+
+//Structure representing BLOCK in version info resource
+struct version_info_block //(always aligned on 32-bit (DWORD) boundary)
+{
+	uint16_t Length; //Length of this block (doesn't include padding)
+	uint16_t ValueLength; //Value length (if any)
+	uint16_t Type; //Value type (0 = binary, 1 = text)
+	uint16_t Key[1]; //Value name (block key) (always NULL terminated)
+
+	//////////
+	//WORD padding1[]; //Padding, if any (ALIGNMENT)
+	//xxxxx Value[]; //Value data, if any (*ALIGNED*)
+	//WORD padding2[]; //Padding, if any (ALIGNMENT)
+	//xxxxx Child[]; //Child block(s), if any (*ALIGNED*)
+	//////////
+};
+
+
+/// IMPORTS ///
+#ifndef SOLARIS
+#pragma pack(push, 8)
+#endif
+struct image_thunk_data64
+{
+	union
+	{
+		uint64_t ForwarderString;  // PBYTE 
+		uint64_t Function;         // PDWORD
+		uint64_t Ordinal;
+		uint64_t AddressOfData;    // PIMAGE_IMPORT_BY_NAME
+	} u1;
+};
+#ifndef SOLARIS
+#pragma pack(pop)
+#endif
+
+struct image_thunk_data32
+{
+	union
+	{
+		uint32_t ForwarderString;      // PBYTE 
+		uint32_t Function;             // PDWORD
+		uint32_t Ordinal;
+		uint32_t AddressOfData;        // PIMAGE_IMPORT_BY_NAME
+	} u1;
+};
+
+struct image_import_descriptor
+{
+	union
+	{
+		uint32_t Characteristics;           // 0 for terminating null import descriptor
+		uint32_t OriginalFirstThunk;        // RVA to original unbound IAT (PIMAGE_THUNK_DATA)
+	};
+
+	uint32_t TimeDateStamp;                 // 0 if not bound,
+											// -1 if bound, and real date\time stamp
+											//     in IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT (new BIND)
+											// O.W. date/time stamp of DLL bound to (Old BIND)
+
+	uint32_t ForwarderChain;                // -1 if no forwarders
+	uint32_t Name;
+	uint32_t FirstThunk;                    // RVA to IAT (if bound this IAT has actual addresses)
+};
+
+
+/// TLS ///
+struct image_tls_directory64
+{
+	uint64_t StartAddressOfRawData;
+	uint64_t EndAddressOfRawData;
+	uint64_t AddressOfIndex;         // PDWORD
+	uint64_t AddressOfCallBacks;     // PIMAGE_TLS_CALLBACK *;
+	uint32_t SizeOfZeroFill;
+	uint32_t Characteristics;
+};
+
+struct image_tls_directory32
+{
+	uint32_t StartAddressOfRawData;
+	uint32_t EndAddressOfRawData;
+	uint32_t AddressOfIndex;             // PDWORD
+	uint32_t AddressOfCallBacks;         // PIMAGE_TLS_CALLBACK *
+	uint32_t SizeOfZeroFill;
+	uint32_t Characteristics;
+};
+
+
+/// Export Format ///
+struct image_export_directory
+{
+	uint32_t Characteristics;
+	uint32_t TimeDateStamp;
+	uint16_t MajorVersion;
+	uint16_t MinorVersion;
+	uint32_t Name;
+	uint32_t Base;
+	uint32_t NumberOfFunctions;
+	uint32_t NumberOfNames;
+	uint32_t AddressOfFunctions;     // RVA from base of image
+	uint32_t AddressOfNames;         // RVA from base of image
+	uint32_t AddressOfNameOrdinals;  // RVA from base of image
+};
+
+
+/// Based relocation format ///
+struct image_base_relocation
+{
+	uint32_t VirtualAddress;
+	uint32_t SizeOfBlock;
+	//  uint16_t TypeOffset[1];
+};
+
+
+/// New format import descriptors pointed to by DataDirectory[ IMAGE_DIRECTORY_ENTRY_BOUND_IMPORT ] ///
+struct image_bound_import_descriptor
+{
+	uint32_t TimeDateStamp;
+	uint16_t OffsetModuleName;
+	uint16_t NumberOfModuleForwarderRefs;
+	// Array of zero or more IMAGE_BOUND_FORWARDER_REF follows
+};
+
+struct image_bound_forwarder_ref
+{
+	uint32_t TimeDateStamp;
+	uint16_t OffsetModuleName;
+	uint16_t Reserved;
+};
+
+
+/// Exception directory ///
+struct image_runtime_function_entry
+{
+	uint32_t BeginAddress;
+	uint32_t EndAddress;
+	uint32_t UnwindInfoAddress;
+};
+
+enum unwind_op_codes
+{
+	uwop_push_nonvol = 0, /* info == register number */
+	uwop_alloc_large,     /* no info, alloc size in next 2 slots */
+	uwop_alloc_small,     /* info == size of allocation / 8 - 1 */
+	uwop_set_fpreg,       /* no info, FP = RSP + UNWIND_INFO.FPRegOffset*16 */
+	uwop_save_nonvol,     /* info == register number, offset in next slot */
+	uwop_save_nonvol_far, /* info == register number, offset in next 2 slots */
+	uwop_save_xmm128,     /* info == XMM reg number, offset in next slot */
+	uwop_save_xmm128_far, /* info == XMM reg number, offset in next 2 slots */
+	uwop_push_machframe   /* info == 0: no error-code, 1: error-code */
+};
+
+union unwind_code
+{
+	struct s
+	{
+		uint8_t CodeOffset;
+		uint8_t UnwindOp : 4;
+		uint8_t OpInfo   : 4;
+	};
+
+	uint16_t FrameOffset;
+};
+
+struct unwind_info
+{
+	uint8_t Version       : 3;
+	uint8_t Flags         : 5;
+	uint8_t SizeOfProlog;
+	uint8_t CountOfCodes;
+	uint8_t FrameRegister : 4;
+	uint8_t FrameOffset   : 4;
+	unwind_code UnwindCode[1];
+	/*  unwind_code MoreUnwindCode[((CountOfCodes + 1) & ~1) - 1];
+	*   union {
+	*       OPTIONAL ULONG ExceptionHandler;
+	*       OPTIONAL ULONG FunctionEntry;
+	*   };
+	*   OPTIONAL ULONG ExceptionData[]; */
+};
+
+
+
+/// Debug ///
+struct image_debug_misc
+{
+	uint32_t DataType;               // type of misc data, see defines
+	uint32_t Length;                 // total length of record, rounded to four
+	// byte multiple.
+	uint8_t  Unicode;                // TRUE if data is unicode string
+	uint8_t  Reserved[3];
+	uint8_t  Data[1];                // Actual data
+};
+
+struct image_coff_symbols_header
+{
+	uint32_t NumberOfSymbols;
+	uint32_t LvaToFirstSymbol;
+	uint32_t NumberOfLinenumbers;
+	uint32_t LvaToFirstLinenumber;
+	uint32_t RvaToFirstByteOfCode;
+	uint32_t RvaToLastByteOfCode;
+	uint32_t RvaToFirstByteOfData;
+	uint32_t RvaToLastByteOfData;
+};
+
+struct image_debug_directory
+{
+	uint32_t Characteristics;
+	uint32_t TimeDateStamp;
+	uint16_t MajorVersion;
+	uint16_t MinorVersion;
+	uint32_t Type;
+	uint32_t SizeOfData;
+	uint32_t AddressOfRawData;
+	uint32_t PointerToRawData;
+};
+
+
+#ifndef SOLARIS
+#pragma pack(push, 2)
+#endif
+struct image_symbol
+{
+	union
+	{
+		uint8_t ShortName[8];
+		struct
+		{
+			uint32_t Short;     // if 0, use LongName
+			uint32_t Long;      // offset into string table
+		} Name;
+		uint32_t LongName[2];    // PBYTE [2]
+	} N;
+	uint32_t Value;
+	int16_t  SectionNumber;
+	uint16_t Type;
+	uint8_t  StorageClass;
+	uint8_t  NumberOfAuxSymbols;
+};
+#ifndef SOLARIS
+#pragma pack(pop)
+#endif
+
+//CodeView Debug OMF signature. The signature at the end of the file is
+//a negative offset from the end of the file to another signature.  At
+//the negative offset (base address) is another signature whose filepos
+//field points to the first OMFDirHeader in a chain of directories.
+//The NB05 signature is used by the link utility to indicated a completely
+//unpacked file. The NB06 signature is used by ilink to indicate that the
+//executable has had CodeView information from an incremental link appended
+//to the executable. The NB08 signature is used by cvpack to indicate that
+//the CodeView Debug OMF has been packed. CodeView will only process
+//executables with the NB08 signature.
+struct OMFSignature
+{
+	char Signature[4];   // "NBxx"
+	uint32_t filepos;    // offset in file
+};
+
+struct CV_INFO_PDB20
+{
+	OMFSignature CvHeader;
+	uint32_t Signature;
+	uint32_t Age;
+	uint8_t PdbFileName[1];
+};
+
+struct CV_INFO_PDB70
+{
+	uint32_t CvSignature;
+	guid Signature;
+	uint32_t Age;
+	uint8_t PdbFileName[1];
+};
+
+//  directory information structure
+//  This structure contains the information describing the directory.
+//  It is pointed to by the signature at the base address or the directory
+//  link field of a preceeding directory.  The directory entries immediately
+//  follow this structure.
+struct OMFDirHeader
+{
+	uint16_t cbDirHeader;    // length of this structure
+	uint16_t cbDirEntry;     // number of bytes in each directory entry
+	uint32_t cDir;           // number of directorie entries
+	int32_t  lfoNextDir;     // offset from base of next directory
+	uint32_t flags;          // status flags
+};
+
+//  directory structure
+//  The data in this structure is used to reference the data for each
+//  subsection of the CodeView Debug OMF information.  Tables that are
+//  not associated with a specific module will have a module index of
+//  oxffff.  These tables are the global types table, the global symbol
+//  table, the global public table and the library table.
+struct OMFDirEntry
+{
+	uint16_t SubSection;     // subsection type (sst...)
+	uint16_t iMod;           // module index
+	int32_t  lfo;            // large file offset of subsection
+	uint32_t cb;             // number of bytes in subsection
+};
+
+
+/// CLR 2.0 header structure ///
+struct image_cor20_header
+{
+	//Header versioning
+	uint32_t cb;
+	uint16_t MajorRuntimeVersion;
+	uint16_t MinorRuntimeVersion;
+
+	// Symbol table and startup information
+	image_data_directory MetaData;
+	uint32_t Flags;
+
+	// If COMIMAGE_FLAGS_NATIVE_ENTRYPOINT is not set, EntryPointToken represents a managed entrypoint.
+	// If COMIMAGE_FLAGS_NATIVE_ENTRYPOINT is set, EntryPointRVA represents an RVA to a native entrypoint.
+	union
+	{
+		uint32_t EntryPointToken;
+		uint32_t EntryPointRVA;
+	};
+
+	// Binding information
+	image_data_directory Resources;
+	image_data_directory StrongNameSignature;
+
+	// Regular fixup and binding information
+	image_data_directory CodeManagerTable;
+	image_data_directory VTableFixups;
+	image_data_directory ExportAddressTableJumps;
+
+	// Precompiled image info (internal use only - set to zero)
+	image_data_directory ManagedNativeHeader;
+};
+
+enum replaces_cor_hdr_numeric_defines
+{
+	// COM+ Header entry point flags.
+	comimage_flags_ilonly               =0x00000001,
+	comimage_flags_32bitrequired        =0x00000002,
+	comimage_flags_il_library           =0x00000004,
+	comimage_flags_strongnamesigned     =0x00000008,
+	comimage_flags_native_entrypoint    =0x00000010,
+	comimage_flags_trackdebugdata       =0x00010000,
+
+	// Version flags for image.
+	cor_version_major_v2                =2,
+	cor_version_major                   =cor_version_major_v2,
+	cor_version_minor                   =0,
+	cor_deleted_name_length             =8,
+	cor_vtablegap_name_length           =8,
+
+	// Maximum size of a NativeType descriptor.
+	native_type_max_cb                  =1,
+	cor_ilmethod_sect_small_max_datasize=0xff,
+
+	// #defines for the MIH FLAGS
+	image_cor_mih_methodrva             =0x01,
+	image_cor_mih_ehrva                 =0x02,
+	image_cor_mih_basicblock            =0x08,
+
+	// V-table constants
+	cor_vtable_32bit                    =0x01,          // V-table slots are 32-bits in size.
+	cor_vtable_64bit                    =0x02,          // V-table slots are 64-bits in size.
+	cor_vtable_from_unmanaged           =0x04,          // If set, transition from unmanaged.
+	cor_vtable_from_unmanaged_retain_appdomain  =0x08,  // If set, transition from unmanaged with keeping the current appdomain.
+	cor_vtable_call_most_derived        =0x10,          // Call most derived method described by
+
+	// EATJ constants
+	image_cor_eatj_thunk_size           =32,            // Size of a jump thunk reserved range.
+
+	// Max name lengths
+	//@todo: Change to unlimited name lengths.
+	max_class_name                      =1024,
+	max_package_name                    =1024
+};
+
+/// Load Configuration Directory Entry ///
+struct image_load_config_directory32
+{
+	uint32_t Size;
+	uint32_t TimeDateStamp;
+	uint16_t MajorVersion;
+	uint16_t MinorVersion;
+	uint32_t GlobalFlagsClear;
+	uint32_t GlobalFlagsSet;
+	uint32_t CriticalSectionDefaultTimeout;
+	uint32_t DeCommitFreeBlockThreshold;
+	uint32_t DeCommitTotalFreeThreshold;
+	uint32_t LockPrefixTable;            // VA
+	uint32_t MaximumAllocationSize;
+	uint32_t VirtualMemoryThreshold;
+	uint32_t ProcessHeapFlags;
+	uint32_t ProcessAffinityMask;
+	uint16_t CSDVersion;
+	uint16_t Reserved1;
+	uint32_t EditList;                   // VA
+	uint32_t SecurityCookie;             // VA
+	uint32_t SEHandlerTable;             // VA
+	uint32_t SEHandlerCount;
+};
+
+struct image_load_config_directory64
+{
+	uint32_t Size;
+	uint32_t TimeDateStamp;
+	uint16_t MajorVersion;
+	uint16_t MinorVersion;
+	uint32_t GlobalFlagsClear;
+	uint32_t GlobalFlagsSet;
+	uint32_t CriticalSectionDefaultTimeout;
+	uint64_t DeCommitFreeBlockThreshold;
+	uint64_t DeCommitTotalFreeThreshold;
+	uint64_t LockPrefixTable;         // VA
+	uint64_t MaximumAllocationSize;
+	uint64_t VirtualMemoryThreshold;
+	uint64_t ProcessAffinityMask;
+	uint32_t ProcessHeapFlags;
+	uint16_t CSDVersion;
+	uint16_t Reserved1;
+	uint64_t EditList;                // VA
+	uint64_t SecurityCookie;          // VA
+	uint64_t SEHandlerTable;          // VA
+	uint64_t SEHandlerCount;
+};
+
+#ifndef SOLARIS
+#pragma pack(pop)
+#endif
+} //namespace pe_win
+
+#ifdef PE_BLISS_WINDOWS
+typedef wchar_t unicode16_t;
+typedef std::basic_string<unicode16_t> u16string;
+#else
+//Instead of wchar_t for windows
+typedef unsigned short unicode16_t;
+typedef std::basic_string<unicode16_t> u16string;
+#endif
+
+} //namespace pe_bliss
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_tls.cpp b/irdb-lib/pebliss/trunk/pe_lib/pe_tls.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..182859f1bf564f0cbc36cfa0b9828a5c9f678e5b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_tls.cpp
@@ -0,0 +1,375 @@
+#include <string.h>
+#include "pe_tls.h"
+#include "pe_properties_generic.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//TLS
+//Default constructor
+tls_info::tls_info()
+	:start_rva_(0), end_rva_(0), index_rva_(0), callbacks_rva_(0),
+	size_of_zero_fill_(0), characteristics_(0)
+{}
+
+//Returns start RVA of TLS raw data
+uint32_t tls_info::get_raw_data_start_rva() const
+{
+	return start_rva_;
+}
+
+//Returns end RVA of TLS raw data
+uint32_t tls_info::get_raw_data_end_rva() const
+{
+	return end_rva_;
+}
+
+//Returns TLS index RVA
+uint32_t tls_info::get_index_rva() const
+{
+	return index_rva_;
+}
+
+//Returns TLS callbacks RVA
+uint32_t tls_info::get_callbacks_rva() const
+{
+	return callbacks_rva_;
+}
+
+//Returns size of zero fill
+uint32_t tls_info::get_size_of_zero_fill() const
+{
+	return size_of_zero_fill_;
+}
+
+//Returns characteristics
+uint32_t tls_info::get_characteristics() const
+{
+	return characteristics_;
+}
+
+//Returns raw TLS data
+const std::string& tls_info::get_raw_data() const
+{
+	return raw_data_;
+}
+
+//Returns TLS callbacks addresses
+const tls_info::tls_callback_list& tls_info::get_tls_callbacks() const
+{
+	return callbacks_;
+}
+
+//Returns TLS callbacks addresses
+tls_info::tls_callback_list& tls_info::get_tls_callbacks()
+{
+	return callbacks_;
+}
+
+//Adds TLS callback
+void tls_info::add_tls_callback(uint32_t rva)
+{
+	callbacks_.push_back(rva);
+}
+
+//Clears TLS callbacks list
+void tls_info::clear_tls_callbacks()
+{
+	callbacks_.clear();
+}
+
+//Recalculates end address of raw TLS data
+void tls_info::recalc_raw_data_end_rva()
+{
+	end_rva_ = static_cast<uint32_t>(start_rva_ + raw_data_.length());
+}
+
+//Sets start RVA of TLS raw data
+void tls_info::set_raw_data_start_rva(uint32_t rva)
+{
+	start_rva_ = rva;
+}
+
+//Sets end RVA of TLS raw data
+void tls_info::set_raw_data_end_rva(uint32_t rva)
+{
+	end_rva_ = rva;
+}
+
+//Sets TLS index RVA
+void tls_info::set_index_rva(uint32_t rva)
+{
+	index_rva_ = rva;
+}
+
+//Sets TLS callbacks RVA
+void tls_info::set_callbacks_rva(uint32_t rva)
+{
+	callbacks_rva_ = rva;
+}
+
+//Sets size of zero fill
+void tls_info::set_size_of_zero_fill(uint32_t size)
+{
+	size_of_zero_fill_ = size;
+}
+
+//Sets characteristics
+void tls_info::set_characteristics(uint32_t characteristics)
+{
+	characteristics_ = characteristics;
+}
+
+//Sets raw TLS data
+void tls_info::set_raw_data(const std::string& data)
+{
+	raw_data_ = data;
+}
+
+//If image does not have TLS, throws an exception
+const tls_info get_tls_info(const pe_base& pe)
+{
+	return pe.get_pe_type() == pe_type_32
+		? get_tls_info_base<pe_types_class_32>(pe)
+		: get_tls_info_base<pe_types_class_64>(pe);
+}
+
+//TLS Rebuilder
+const image_directory rebuild_tls(pe_base& pe, const tls_info& info, section& tls_section, uint32_t offset_from_section_start, bool write_tls_callbacks, bool write_tls_data, tls_data_expand_type expand, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	return pe.get_pe_type() == pe_type_32
+		? rebuild_tls_base<pe_types_class_32>(pe, info, tls_section, offset_from_section_start, write_tls_callbacks, write_tls_data, expand, save_to_pe_header, auto_strip_last_section)
+		: rebuild_tls_base<pe_types_class_64>(pe, info, tls_section, offset_from_section_start, write_tls_callbacks, write_tls_data, expand, save_to_pe_header, auto_strip_last_section);
+}
+
+//Get TLS info
+//If image does not have TLS, throws an exception
+template<typename PEClassType>
+const tls_info get_tls_info_base(const pe_base& pe)
+{
+	tls_info ret;
+
+	//If there's no TLS directory, throw an exception
+	if(!pe.has_tls())
+		throw pe_exception("Image does not have TLS directory", pe_exception::directory_does_not_exist);
+
+	//Get TLS directory data
+	typename PEClassType::TLSStruct tls_directory_data = pe.section_data_from_rva<typename PEClassType::TLSStruct>(pe.get_directory_rva(image_directory_entry_tls), section_data_virtual, true);
+
+	//Check data addresses
+	if(tls_directory_data.EndAddressOfRawData == tls_directory_data.StartAddressOfRawData)
+	{
+		try
+		{
+			pe.va_to_rva(static_cast<typename PEClassType::BaseSize>(tls_directory_data.EndAddressOfRawData));
+		}
+		catch(const pe_exception&)
+		{
+			//Fix addressess on incorrect conversion
+			tls_directory_data.EndAddressOfRawData = tls_directory_data.StartAddressOfRawData = 0;
+		}
+	}
+
+	if(tls_directory_data.StartAddressOfRawData &&
+		pe.section_data_length_from_va(static_cast<typename PEClassType::BaseSize>(tls_directory_data.StartAddressOfRawData),
+		static_cast<typename PEClassType::BaseSize>(tls_directory_data.StartAddressOfRawData), section_data_virtual, true)
+		< (tls_directory_data.EndAddressOfRawData - tls_directory_data.StartAddressOfRawData))
+		throw pe_exception("Incorrect TLS directory", pe_exception::incorrect_tls_directory);
+
+	//Fill TLS info
+	//VAs are not checked
+	ret.set_raw_data_start_rva(tls_directory_data.StartAddressOfRawData ? pe.va_to_rva(static_cast<typename PEClassType::BaseSize>(tls_directory_data.StartAddressOfRawData)) : 0);
+	ret.set_raw_data_end_rva(tls_directory_data.EndAddressOfRawData ? pe.va_to_rva(static_cast<typename PEClassType::BaseSize>(tls_directory_data.EndAddressOfRawData)) : 0);
+	ret.set_index_rva(tls_directory_data.AddressOfIndex ? pe.va_to_rva(static_cast<typename PEClassType::BaseSize>(tls_directory_data.AddressOfIndex)) : 0);
+	ret.set_callbacks_rva(tls_directory_data.AddressOfCallBacks ? pe.va_to_rva(static_cast<typename PEClassType::BaseSize>(tls_directory_data.AddressOfCallBacks)) : 0);
+	ret.set_size_of_zero_fill(tls_directory_data.SizeOfZeroFill);
+	ret.set_characteristics(tls_directory_data.Characteristics);
+
+	if(tls_directory_data.StartAddressOfRawData && tls_directory_data.StartAddressOfRawData != tls_directory_data.EndAddressOfRawData)
+	{
+		//Read and save TLS RAW data
+		ret.set_raw_data(std::string(
+			pe.section_data_from_va(static_cast<typename PEClassType::BaseSize>(tls_directory_data.StartAddressOfRawData), section_data_virtual, true),
+			static_cast<uint32_t>(tls_directory_data.EndAddressOfRawData - tls_directory_data.StartAddressOfRawData)));
+	}
+
+	//If file has TLS callbacks
+	if(ret.get_callbacks_rva())
+	{
+		//Read callbacks VAs
+		uint32_t current_tls_callback = 0;
+
+		while(true)
+		{
+			//Read TLS callback VA
+			typename PEClassType::BaseSize va = pe.section_data_from_va<typename PEClassType::BaseSize>(static_cast<typename PEClassType::BaseSize>(tls_directory_data.AddressOfCallBacks + current_tls_callback), section_data_virtual, true);
+			if(va == 0)
+				break;
+
+			//Save it
+			ret.add_tls_callback(pe.va_to_rva(va, false));
+
+			//Move to next callback VA
+			current_tls_callback += sizeof(va);
+		}
+	}
+
+	return ret;
+}
+
+//Rebuilder of TLS structures
+//If write_tls_callbacks = true, TLS callbacks VAs will be written to their place
+//If write_tls_data = true, TLS data will be written to its place
+//If you have chosen to rewrite raw data, only (EndAddressOfRawData - StartAddressOfRawData) bytes will be written, not the full length of string
+//representing raw data content
+//auto_strip_last_section - if true and TLS are placed in the last section, it will be automatically stripped
+//Note/TODO: TLS Callbacks array is not DWORD-aligned (seems to work on WinXP - Win7)
+template<typename PEClassType>
+const image_directory rebuild_tls_base(pe_base& pe, const tls_info& info, section& tls_section, uint32_t offset_from_section_start, bool write_tls_callbacks, bool write_tls_data, tls_data_expand_type expand, bool save_to_pe_header, bool auto_strip_last_section)
+{
+	//Check that tls_section is attached to this PE image
+	if(!pe.section_attached(tls_section))
+		throw pe_exception("TLS section must be attached to PE file", pe_exception::section_is_not_attached);
+	
+	uint32_t tls_data_pos = pe_utils::align_up(offset_from_section_start, sizeof(typename PEClassType::BaseSize));
+	uint32_t needed_size = sizeof(typename PEClassType::TLSStruct); //Calculate needed size for TLS table
+	
+	//Check if tls_section is last one. If it's not, check if there's enough place for TLS data
+	if(&tls_section != &*(pe.get_image_sections().end() - 1) && 
+		(tls_section.empty() || pe_utils::align_up(tls_section.get_size_of_raw_data(), pe.get_file_alignment()) < needed_size + tls_data_pos))
+		throw pe_exception("Insufficient space for TLS directory", pe_exception::insufficient_space);
+
+	//Check raw data positions
+	if(info.get_raw_data_end_rva() < info.get_raw_data_start_rva() || info.get_index_rva() == 0)
+		throw pe_exception("Incorrect TLS directory", pe_exception::incorrect_tls_directory);
+
+	std::string& raw_data = tls_section.get_raw_data();
+
+	//This will be done only if tls_section is the last section of image or for section with unaligned raw length of data
+	if(raw_data.length() < needed_size + tls_data_pos)
+		raw_data.resize(needed_size + tls_data_pos); //Expand section raw data
+
+	//Create and fill TLS structure
+	typename PEClassType::TLSStruct tls_struct = {0};
+	
+	typename PEClassType::BaseSize va;
+	if(info.get_raw_data_start_rva())
+	{
+		pe.rva_to_va(info.get_raw_data_start_rva(), va);
+		tls_struct.StartAddressOfRawData = va;
+		tls_struct.SizeOfZeroFill = info.get_size_of_zero_fill();
+	}
+
+	if(info.get_raw_data_end_rva())
+	{
+		pe.rva_to_va(info.get_raw_data_end_rva(), va);
+		tls_struct.EndAddressOfRawData = va;
+	}
+
+	pe.rva_to_va(info.get_index_rva(), va);
+	tls_struct.AddressOfIndex = va;
+
+	if(info.get_callbacks_rva())
+	{
+		pe.rva_to_va(info.get_callbacks_rva(), va);
+		tls_struct.AddressOfCallBacks = va;
+	}
+
+	tls_struct.Characteristics = info.get_characteristics();
+
+	//Save TLS structure
+	memcpy(&raw_data[tls_data_pos], &tls_struct, sizeof(tls_struct));
+
+	//If we are asked to rewrite TLS raw data
+	if(write_tls_data && info.get_raw_data_start_rva() && info.get_raw_data_start_rva() != info.get_raw_data_end_rva())
+	{
+		try
+		{
+			//Check if we're going to write TLS raw data to an existing section (not to PE headers)
+			section& raw_data_section = pe.section_from_rva(info.get_raw_data_start_rva());
+			pe.expand_section(raw_data_section, info.get_raw_data_start_rva(), info.get_raw_data_end_rva() - info.get_raw_data_start_rva(), expand == tls_data_expand_raw ? pe_base::expand_section_raw : pe_base::expand_section_virtual);
+		}
+		catch(const pe_exception&)
+		{
+			//If no section is presented by StartAddressOfRawData, just go to next step
+		}
+
+		unsigned long write_raw_data_size = info.get_raw_data_end_rva() - info.get_raw_data_start_rva();
+		unsigned long available_raw_length = 0;
+
+		//Check if there's enough RAW space to write raw TLS data...
+		if((available_raw_length = pe.section_data_length_from_rva(info.get_raw_data_start_rva(), info.get_raw_data_start_rva(), section_data_raw, true))
+			< info.get_raw_data_end_rva() - info.get_raw_data_start_rva())
+		{
+			//Check if there's enough virtual space for it...
+			if(pe.section_data_length_from_rva(info.get_raw_data_start_rva(), info.get_raw_data_start_rva(), section_data_virtual, true)
+				< info.get_raw_data_end_rva() - info.get_raw_data_start_rva())
+				throw pe_exception("Insufficient space for TLS raw data", pe_exception::insufficient_space);
+			else
+				write_raw_data_size = available_raw_length; //We'll write just a part of full raw data
+		}
+
+		//Write raw TLS data, if any
+		if(write_raw_data_size != 0)
+			memcpy(pe.section_data_from_rva(info.get_raw_data_start_rva(), true), info.get_raw_data().data(), write_raw_data_size);
+	}
+
+	//If we are asked to rewrite TLS callbacks addresses
+	if(write_tls_callbacks && info.get_callbacks_rva())
+	{
+		unsigned long needed_callback_size = static_cast<unsigned long>((info.get_tls_callbacks().size() + 1 /* last null element */) * sizeof(typename PEClassType::BaseSize));
+
+		try
+		{
+			//Check if we're going to write TLS callbacks VAs to an existing section (not to PE headers)
+			section& raw_data_section = pe.section_from_rva(info.get_callbacks_rva());
+			pe.expand_section(raw_data_section, info.get_callbacks_rva(), needed_callback_size, pe_base::expand_section_raw);
+		}
+		catch(const pe_exception&)
+		{
+			//If no section is presented by RVA of callbacks, just go to next step
+		}
+
+		//Check if there's enough space to write callbacks TLS data...
+		if(pe.section_data_length_from_rva(info.get_callbacks_rva(), info.get_callbacks_rva(), section_data_raw, true)
+			< needed_callback_size - sizeof(typename PEClassType::BaseSize) /* last zero element can be virtual only */)
+			throw pe_exception("Insufficient space for TLS callbacks data", pe_exception::insufficient_space);
+		
+		if(pe.section_data_length_from_rva(info.get_callbacks_rva(), info.get_callbacks_rva(), section_data_virtual, true)
+			< needed_callback_size /* check here full virtual data length available */)
+			throw pe_exception("Insufficient space for TLS callbacks data", pe_exception::insufficient_space);
+
+		std::vector<typename PEClassType::BaseSize> callbacks_virtual_addresses;
+		callbacks_virtual_addresses.reserve(info.get_tls_callbacks().size() + 1 /* last null element */);
+
+		//Convert TLS RVAs to VAs
+		for(tls_info::tls_callback_list::const_iterator it = info.get_tls_callbacks().begin(); it != info.get_tls_callbacks().end(); ++it)
+		{
+			typename PEClassType::BaseSize cb_va = 0;
+			pe.rva_to_va(*it, cb_va);
+			callbacks_virtual_addresses.push_back(cb_va);
+		}
+
+		//Ending null element
+		callbacks_virtual_addresses.push_back(0);
+
+		//Write callbacks TLS data
+		memcpy(pe.section_data_from_rva(info.get_callbacks_rva(), true), &callbacks_virtual_addresses[0], needed_callback_size);
+	}
+	
+	//Adjust section raw and virtual sizes
+	pe.recalculate_section_sizes(tls_section, auto_strip_last_section);
+
+	image_directory ret(pe.rva_from_section_offset(tls_section, tls_data_pos), needed_size);
+
+	//If auto-rewrite of PE headers is required
+	if(save_to_pe_header)
+	{
+		pe.set_directory_rva(image_directory_entry_tls, ret.get_rva());
+		pe.set_directory_size(image_directory_entry_tls, ret.get_size());
+	}
+
+	return ret;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/pe_tls.h b/irdb-lib/pebliss/trunk/pe_lib/pe_tls.h
new file mode 100644
index 0000000000000000000000000000000000000000..9f66753c0051578034024b7962a612c03300efac
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/pe_tls.h
@@ -0,0 +1,104 @@
+#ifndef pebliss_pe_tls_h
+#define pebliss_pe_tls_h
+#pragma once
+#include <memory>
+#include <istream>
+#include "pe_base.h"
+#include "pe_directory.h"
+
+namespace pe_bliss
+{
+//Class representing TLS info
+//We use "DWORD" type to represent RVAs, because RVA is
+//always 32bit even in PE+
+class tls_info
+{
+public:
+	typedef std::vector<uint32_t> tls_callback_list;
+
+public:
+	//Default constructor
+	tls_info();
+
+	//Returns start RVA of TLS raw data
+	uint32_t get_raw_data_start_rva() const;
+	//Returns end RVA of TLS raw data
+	uint32_t get_raw_data_end_rva() const;
+	//Returns TLS index RVA
+	uint32_t get_index_rva() const;
+	//Returns TLS callbacks RVA
+	uint32_t get_callbacks_rva() const;
+	//Returns size of zero fill
+	uint32_t get_size_of_zero_fill() const;
+	//Returns characteristics
+	uint32_t get_characteristics() const;
+	//Returns raw TLS data
+	const std::string& get_raw_data() const;
+	//Returns TLS callbacks addresses
+	const tls_callback_list& get_tls_callbacks() const;
+
+public: //These functions do not change everything inside image, they are used by PE class
+	//You can also use them to rebuild TLS directory
+
+	//Sets start RVA of TLS raw data
+	void set_raw_data_start_rva(uint32_t rva);
+	//Sets end RVA of TLS raw data
+	void set_raw_data_end_rva(uint32_t rva);
+	//Sets TLS index RVA
+	void set_index_rva(uint32_t rva);
+	//Sets TLS callbacks RVA
+	void set_callbacks_rva(uint32_t rva);
+	//Sets size of zero fill
+	void set_size_of_zero_fill(uint32_t size);
+	//Sets characteristics
+	void set_characteristics(uint32_t characteristics);
+	//Sets raw TLS data
+	void set_raw_data(const std::string& data);
+	//Returns TLS callbacks addresses
+	tls_callback_list& get_tls_callbacks();
+	//Adds TLS callback
+	void add_tls_callback(uint32_t rva);
+	//Clears TLS callbacks list
+	void clear_tls_callbacks();
+	//Recalculates end address of raw TLS data
+	void recalc_raw_data_end_rva();
+
+private:
+	uint32_t start_rva_, end_rva_, index_rva_, callbacks_rva_;
+	uint32_t size_of_zero_fill_, characteristics_;
+
+	//Raw TLS data
+	std::string raw_data_;
+
+	//TLS callback RVAs
+	tls_callback_list callbacks_;
+};
+
+//Represents type of expanding of TLS section containing raw data
+//(Works only if you are writing TLS raw data to tls_section and it is the last one in the PE image on the moment of TLS rebuild)
+enum tls_data_expand_type
+{
+	tls_data_expand_raw, //If there is not enough raw space for raw TLS data, it can be expanded
+	tls_data_expand_virtual //If there is not enough virtual place for raw TLS data, it can be expanded
+};
+
+
+//Get TLS info
+//If image does not have TLS, throws an exception
+const tls_info get_tls_info(const pe_base& pe);
+
+template<typename PEClassType>
+const tls_info get_tls_info_base(const pe_base& pe);
+	
+//Rebuilder of TLS structures
+//If write_tls_callbacks = true, TLS callbacks VAs will be written to their place
+//If write_tls_data = true, TLS data will be written to its place
+//If you have chosen to rewrite raw data, only (EndAddressOfRawData - StartAddressOfRawData) bytes will be written, not the full length of string
+//representing raw data content
+//auto_strip_last_section - if true and TLS are placed in the last section, it will be automatically stripped
+const image_directory rebuild_tls(pe_base& pe, const tls_info& info, section& tls_section, uint32_t offset_from_section_start = 0, bool write_tls_callbacks = true, bool write_tls_data = true, tls_data_expand_type expand = tls_data_expand_raw, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+
+template<typename PEClassType>
+const image_directory rebuild_tls_base(pe_base& pe, const tls_info& info, section& tls_section, uint32_t offset_from_section_start = 0, bool write_tls_callbacks = true, bool write_tls_data = true, tls_data_expand_type expand = tls_data_expand_raw, bool save_to_pe_header = true, bool auto_strip_last_section = true);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/readme.txt b/irdb-lib/pebliss/trunk/pe_lib/readme.txt
new file mode 100644
index 0000000000000000000000000000000000000000..f52e7a568dfca20f839c8ea202be51d0a78c18a5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/readme.txt
@@ -0,0 +1,30 @@
+Îòêðûòàÿ áåñïëàòíàÿ áèáëèîòåêà äëÿ ðàáîòû ñ PE-ôàéëàìè PE Bliss.
+Áåñïëàòíà ê èñïîëüçîâàíèþ, ìîäèôèêàöèè è ðàñïðîñòðàíåíèþ.
+Àâòîð: DX
+(c) DX 2011-2012, kaimi.ru
+
+Ñîâìåñòèìîñòü: Windows, Linux
+
+Âîçìîæíîñòè:
+[+] Ñîçäàíèå PE èëè PE+ ôàéëà ñ íóëÿ
+[+] ×òåíèå 32-ðàçðÿäíûõ è 64-ðàçðÿäíûõ PE-ôàéëîâ (PE, PE+) è åäèíîîáðàçíàÿ ðàáîòà ñ íèìè
+[+] Ïåðåñáîðêà 32-ðàçðÿäíûõ è 64-ðàçðÿäíûõ PE-ôàéëîâ
+[+] Ðàáîòà ñ äèðåêòîðèÿìè è çàãîëîâêàìè
+[+] Êîíâåðòèðîâàíèå àäðåñîâ
+[+] ×òåíèå è ðåäàêòèðîâàíèå ñåêöèé PE-ôàéëà
+[+] ×òåíèå è ðåäàêòèðîâàíèå òàáëèöû èìïîðòîâ
+[+] ×òåíèå è ðåäàêòèðîâàíèå òàáëèöû ýêñïîðòîâ
+[+] ×òåíèå è ðåäàêòèðîâàíèå òàáëèö ðåëîêàöèé
+[+] ×òåíèå è ðåäàêòèðîâàíèå ðåñóðñîâ
+[+] ×òåíèå è ðåäàêòèðîâàíèå TLS
+[+] ×òåíèå è ðåäàêòèðîâàíèå êîíôèãóðàöèè îáðàçà (image config)
+[+] ×òåíèå áàçîâîé èíôîðìàöèè .NET
+[+] ×òåíèå è ðåäàêòèðîâàíèå èíôîðìàöèè î ïðèâÿçàííîì èìïîðòå
+[+] ×òåíèå äèðåêòîðèè èñêëþ÷åíèé (òîëüêî PE+)
+[+] ×òåíèå îòëàäî÷íîé äèðåêòîðèè ñ ðàñøèðåííîé èíôîðìàöèåé
+[+] Âû÷èñëåíèå ýíòðîïèè
+[+] Èçìåíåíèå ôàéëîâîãî âûðàâíèâàíèÿ
+[+] Èçìåíåíèå áàçîâîãî àäðåñà çàãðóçêè
+[+] Ðàáîòà ñ DOS Stub'îì è Rich overlay
+[+] Âûñîêîóðîâíåâîå ÷òåíèå ðåñóðñîâ: êàðòèíêè, èêîíêè, êóðñîðû, èíôîðìàöèÿ î âåðñèè, ñòðîêîâûå òàáëèöû, òàáëèöû ñîîáùåíèé
+[+] Âûñîêîóðîâíåâîå ðåäàêòèðîâàíèå ðåñóðñîâ: êàðòèíêè, èêîíêè, êóðñîðû, èíôîðìàöèÿ î âåðñèè
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_reader.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_reader.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..29eff549db94f625677ae8940079e4d76d564044
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_reader.cpp
@@ -0,0 +1,65 @@
+#include <cmath>
+#include "resource_bitmap_reader.h"
+#include "pe_resource_viewer.h"
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+resource_bitmap_reader::resource_bitmap_reader(const pe_resource_viewer& res)
+	:res_(res)
+{}
+
+//Returns bitmap data by name and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_bitmap_reader::get_bitmap_by_name(const std::wstring& name, uint32_t index) const
+{
+	return create_bitmap(res_.get_resource_data_by_name(pe_resource_viewer::resource_bitmap, name, index).get_data());
+}
+
+//Returns bitmap data by name and language (minimum checks of format correctness)
+const std::string resource_bitmap_reader::get_bitmap_by_name(uint32_t language, const std::wstring& name) const
+{
+	return create_bitmap(res_.get_resource_data_by_name(language, pe_resource_viewer::resource_bitmap, name).get_data());
+}
+
+//Returns bitmap data by ID and language (minimum checks of format correctness)
+const std::string resource_bitmap_reader::get_bitmap_by_id_lang(uint32_t language, uint32_t id) const
+{
+	return create_bitmap(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_bitmap, id).get_data());
+}
+
+//Returns bitmap data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_bitmap_reader::get_bitmap_by_id(uint32_t id, uint32_t index) const
+{
+	return create_bitmap(res_.get_resource_data_by_id(pe_resource_viewer::resource_bitmap, id, index).get_data());
+}
+
+//Helper function of creating bitmap header
+const std::string resource_bitmap_reader::create_bitmap(const std::string& resource_data)
+{
+	//Create bitmap file header
+	bitmapfileheader header = {0};
+	header.bfType = 0x4d42; //Signature "BM"
+	header.bfOffBits = sizeof(bitmapfileheader) + sizeof(bitmapinfoheader); //Offset to bitmap bits
+	header.bfSize = static_cast<uint32_t>(sizeof(bitmapfileheader) + resource_data.length()); //Size of bitmap
+
+	//Check size of resource data
+	if(resource_data.length() < sizeof(bitmapinfoheader))
+		throw pe_exception("Incorrect resource bitmap", pe_exception::resource_incorrect_bitmap);
+
+	{
+		//Get bitmap info header
+		const bitmapinfoheader* info = reinterpret_cast<const bitmapinfoheader*>(resource_data.data());
+
+		//If color table is present, skip it
+		if(info->biClrUsed != 0)
+			header.bfOffBits += 4 * info->biClrUsed; //Add this size to offset to bitmap bits
+		else if(info->biBitCount <= 8)
+			header.bfOffBits += 4 * static_cast<uint32_t>(std::pow(2.f, info->biBitCount)); //Add this size to offset to bitmap bits
+	}
+
+	//Return final bitmap data
+	return std::string(reinterpret_cast<const char*>(&header), sizeof(bitmapfileheader)) + resource_data;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_reader.h b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_reader.h
new file mode 100644
index 0000000000000000000000000000000000000000..e518c415577567a630a4c1f352d9cfca0abf7600
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_reader.h
@@ -0,0 +1,32 @@
+#ifndef pebliss_resource_bitmap_reader_h
+#define pebliss_resource_bitmap_reader_h
+#pragma once
+#include <string>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+class pe_resource_viewer;
+
+class resource_bitmap_reader
+{
+public:
+	resource_bitmap_reader(const pe_resource_viewer& res);
+
+	//Returns bitmap data by name and language (minimum checks of format correctness)
+	const std::string get_bitmap_by_name(uint32_t language, const std::wstring& name) const;
+	//Returns bitmap data by name and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_bitmap_by_name(const std::wstring& name, uint32_t index = 0) const;
+	//Returns bitmap data by ID and language (minimum checks of format correctness)
+	const std::string get_bitmap_by_id_lang(uint32_t language, uint32_t id) const;
+	//Returns bitmap data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_bitmap_by_id(uint32_t id, uint32_t index = 0) const;
+
+private:
+	//Helper function of creating bitmap header
+	static const std::string create_bitmap(const std::string& resource_data);
+
+	const pe_resource_viewer& res_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_writer.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_writer.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..2a28ff6e68b8ddb5cec46e57e652fabb89954a47
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_writer.cpp
@@ -0,0 +1,54 @@
+#include "resource_bitmap_writer.h"
+#include "pe_resource_manager.h"
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+resource_bitmap_writer::resource_bitmap_writer(pe_resource_manager& res)
+	:res_(res)
+{}
+
+//Adds bitmap from bitmap file data. If bitmap already exists, replaces it
+//timestamp will be used for directories that will be added
+void resource_bitmap_writer::add_bitmap(const std::string& bitmap_file, uint32_t id, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	//Check bitmap data a little
+	if(bitmap_file.length() < sizeof(bitmapfileheader))
+		throw pe_exception("Incorrect resource bitmap", pe_exception::resource_incorrect_bitmap);
+
+	resource_directory_entry new_entry;
+	new_entry.set_id(id);
+
+	//Add bitmap
+	res_.add_resource(bitmap_file.substr(sizeof(bitmapfileheader)), pe_resource_viewer::resource_bitmap, new_entry, resource_directory::entry_finder(id), language, codepage, timestamp);
+}
+
+//Adds bitmap from bitmap file data. If bitmap already exists, replaces it
+//timestamp will be used for directories that will be added
+void resource_bitmap_writer::add_bitmap(const std::string& bitmap_file, const std::wstring& name, uint32_t language, uint32_t codepage, uint32_t timestamp)
+{
+	//Check bitmap data a little
+	if(bitmap_file.length() < sizeof(bitmapfileheader))
+		throw pe_exception("Incorrect resource bitmap", pe_exception::resource_incorrect_bitmap);
+
+	resource_directory_entry new_entry;
+	new_entry.set_name(name);
+
+	//Add bitmap
+	res_.add_resource(bitmap_file.substr(sizeof(bitmapfileheader)), pe_resource_viewer::resource_bitmap, new_entry, resource_directory::entry_finder(name), language, codepage, timestamp);
+}
+
+//Removes bitmap by name/ID and language
+bool resource_bitmap_writer::remove_bitmap(const std::wstring& name, uint32_t language)
+{
+	return res_.remove_resource(pe_resource_viewer::resource_bitmap, name, language);
+}
+
+//Removes bitmap by name/ID and language
+bool resource_bitmap_writer::remove_bitmap(uint32_t id, uint32_t language)
+{
+	return res_.remove_resource(pe_resource_viewer::resource_bitmap, id, language);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_writer.h b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_writer.h
new file mode 100644
index 0000000000000000000000000000000000000000..d3ccff2fac5281ed1f4b5382d5f9249b9dc26876
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_bitmap_writer.h
@@ -0,0 +1,29 @@
+#ifndef pebliss_resource_bitmap_writer_h
+#define pebliss_resource_bitmap_writer_h
+#pragma once
+#include <string>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+class pe_resource_manager;
+
+class resource_bitmap_writer
+{
+public:
+	resource_bitmap_writer(pe_resource_manager& res);
+
+	//Adds bitmap from bitmap file data. If bitmap already exists, replaces it
+	//timestamp will be used for directories that will be added
+	void add_bitmap(const std::string& bitmap_file, uint32_t id, uint32_t language, uint32_t codepage = 0, uint32_t timestamp = 0);
+	void add_bitmap(const std::string& bitmap_file, const std::wstring& name, uint32_t language, uint32_t codepage = 0, uint32_t timestamp = 0);
+
+	//Removes bitmap by name/ID and language
+	bool remove_bitmap(const std::wstring& name, uint32_t language);
+	bool remove_bitmap(uint32_t id, uint32_t language);
+
+private:
+	pe_resource_manager& res_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_reader.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_reader.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..514e288c225b7aaa4c2df7f13b36413c27f8b07a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_reader.cpp
@@ -0,0 +1,500 @@
+#include <algorithm>
+#include "resource_cursor_icon_reader.h"
+#include "pe_structures.h"
+#include "pe_resource_viewer.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+resource_cursor_icon_reader::resource_cursor_icon_reader(const pe_resource_viewer& res)
+	:res_(res)
+{}
+
+//Helper function of creating icon headers from ICON_GROUP resource data
+//Returns icon count
+uint16_t resource_cursor_icon_reader::format_icon_headers(std::string& ico_data, const std::string& resource_data)
+{
+	//Check resource data size
+	if(resource_data.length() < sizeof(ico_header))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	//Get icon header
+	const ico_header* info = reinterpret_cast<const ico_header*>(resource_data.data());
+
+	//Check resource data size
+	if(resource_data.length() < sizeof(ico_header) + info->Count * sizeof(icon_group))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	//Reserve memory to speed up a little
+	ico_data.reserve(sizeof(ico_header) + info->Count * sizeof(icondirentry));
+	ico_data.append(reinterpret_cast<const char*>(info), sizeof(ico_header));
+
+	//Iterate over all listed icons
+	uint32_t offset = sizeof(ico_header) + sizeof(icondirentry) * info->Count;
+	for(uint16_t i = 0; i != info->Count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(resource_data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+
+		//Fill icon data
+		icondirentry direntry;
+		direntry.BitCount = group->BitCount;
+		direntry.ColorCount = group->ColorCount;
+		direntry.Height = group->Height;
+		direntry.Planes = group->Planes;
+		direntry.Reserved = group->Reserved;
+		direntry.SizeInBytes = group->SizeInBytes;
+		direntry.Width = group->Width;
+		direntry.ImageOffset = offset;
+
+		//Add icon header to returned value
+		ico_data.append(reinterpret_cast<const char*>(&direntry), sizeof(icondirentry));
+
+		offset += group->SizeInBytes;
+	}
+
+	//Return icon count
+	return info->Count;
+}
+
+//Returns single icon data by ID and language (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_single_icon_by_id_lang(uint32_t language, uint32_t id) const
+{
+	//Get icon headers
+	std::string icon_data(lookup_icon_group_data_by_icon(id, language));
+	//Append icon data
+	icon_data.append(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon, id).get_data());
+	return icon_data;
+}
+
+//Returns single icon data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_single_icon_by_id(uint32_t id, uint32_t index) const
+{
+	pe_resource_viewer::resource_language_list languages(res_.list_resource_languages(pe_resource_viewer::resource_icon, id));
+	if(languages.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+
+	//Get icon headers
+	std::string icon_data(lookup_icon_group_data_by_icon(id, languages.at(index)));
+	//Append icon data
+	icon_data.append(res_.get_resource_data_by_id(pe_resource_viewer::resource_icon, id, index).get_data());
+	return icon_data;
+}
+
+//Returns icon data by name and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_icon_by_name(const std::wstring& name, uint32_t index) const
+{
+	std::string ret;
+
+	//Get resource by name and index
+	const std::string data = res_.get_resource_data_by_name(pe_resource_viewer::resource_icon_group, name, index).get_data();
+
+	//Create icon headers
+	uint16_t icon_count = format_icon_headers(ret, data);
+
+	//Append icon data
+	for(uint16_t i = 0; i != icon_count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+		ret += res_.get_resource_data_by_id(pe_resource_viewer::resource_icon, group->Number, index).get_data();
+	}
+
+	return ret;
+}
+
+//Returns icon data by name and language (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_icon_by_name(uint32_t language, const std::wstring& name) const
+{
+	std::string ret;
+
+	//Get resource by name and language
+	const std::string data = res_.get_resource_data_by_name(language, pe_resource_viewer::resource_icon_group, name).get_data();
+
+	//Create icon headers
+	uint16_t icon_count = format_icon_headers(ret, data);
+
+	//Append icon data
+	for(uint16_t i = 0; i != icon_count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+		ret += res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon, group->Number).get_data();
+	}
+
+	return ret;
+}
+
+//Returns icon data by ID and language (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_icon_by_id_lang(uint32_t language, uint32_t id) const
+{
+	std::string ret;
+
+	//Get resource by language and id
+	const std::string data = res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon_group, id).get_data();
+
+	//Create icon headers
+	uint16_t icon_count = format_icon_headers(ret, data);
+
+	//Append icon data
+	for(uint16_t i = 0; i != icon_count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+		ret += res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon, group->Number).get_data();
+	}
+
+	return ret;
+}
+
+//Returns icon data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_icon_by_id(uint32_t id, uint32_t index) const
+{
+	std::string ret;
+
+	//Get resource by id and index
+	const std::string data = res_.get_resource_data_by_id(pe_resource_viewer::resource_icon_group, id, index).get_data();
+
+	//Create icon headers
+	uint16_t icon_count = format_icon_headers(ret, data);
+
+	//Append icon data
+	for(uint16_t i = 0; i != icon_count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+		ret += res_.get_resource_data_by_id(pe_resource_viewer::resource_icon, group->Number, index).get_data();
+	}
+
+	return ret;
+}
+
+//Checks for icon presence inside icon group, fills icon headers if found
+bool resource_cursor_icon_reader::check_icon_presence(const std::string& icon_group_resource_data, uint32_t icon_id, std::string& ico_data)
+{
+	//Check resource data size
+	if(icon_group_resource_data.length() < sizeof(ico_header))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	//Get icon header
+	const ico_header* info = reinterpret_cast<const ico_header*>(icon_group_resource_data.data());
+
+	//Check resource data size
+	if(icon_group_resource_data.length() < sizeof(ico_header) + info->Count * sizeof(icon_group))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	for(uint16_t i = 0; i != info->Count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(icon_group_resource_data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+		if(group->Number == icon_id)
+		{
+			//Reserve memory to speed up a little
+			ico_data.reserve(sizeof(ico_header) + sizeof(icondirentry));
+			//Write single-icon icon header
+			ico_header new_header = *info;
+			new_header.Count = 1;
+			ico_data.append(reinterpret_cast<const char*>(&new_header), sizeof(ico_header));
+
+			//Fill icon data
+			icondirentry direntry;
+			direntry.BitCount = group->BitCount;
+			direntry.ColorCount = group->ColorCount;
+			direntry.Height = group->Height;
+			direntry.Planes = group->Planes;
+			direntry.Reserved = group->Reserved;
+			direntry.SizeInBytes = group->SizeInBytes;
+			direntry.Width = group->Width;
+			direntry.ImageOffset = sizeof(ico_header) + sizeof(icondirentry);
+			ico_data.append(reinterpret_cast<const char*>(&direntry), sizeof(direntry));
+
+			return true;
+		}
+	}
+
+	return false;
+}
+
+//Looks up icon group by icon id and returns full icon headers if found
+const std::string resource_cursor_icon_reader::lookup_icon_group_data_by_icon(uint32_t icon_id, uint32_t language) const
+{
+	std::string icon_header_data;
+
+	{
+		//List all ID-resources
+		pe_resource_viewer::resource_id_list ids(res_.list_resource_ids(pe_resource_viewer::resource_icon_group));
+
+		for(pe_resource_viewer::resource_id_list::const_iterator it = ids.begin(); it != ids.end(); ++it)
+		{
+			pe_resource_viewer::resource_language_list group_languages(res_.list_resource_languages(pe_resource_viewer::resource_icon_group, *it));
+			if(std::find(group_languages.begin(), group_languages.end(), language) != group_languages.end()
+				&& check_icon_presence(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon_group, *it).get_data(), icon_id, icon_header_data))
+				return icon_header_data;
+		}
+	}
+
+	{
+		//List all named resources
+		pe_resource_viewer::resource_name_list names(res_.list_resource_names(pe_resource_viewer::resource_icon_group));
+		for(pe_resource_viewer::resource_name_list::const_iterator it = names.begin(); it != names.end(); ++it)
+		{
+			pe_resource_viewer::resource_language_list group_languages(res_.list_resource_languages(pe_resource_viewer::resource_icon_group, *it));
+			if(std::find(group_languages.begin(), group_languages.end(), language) != group_languages.end()
+				&& check_icon_presence(res_.get_resource_data_by_name(language, pe_resource_viewer::resource_icon_group, *it).get_data(), icon_id, icon_header_data))
+				return icon_header_data;
+		}
+	}
+
+	throw pe_exception("No icon group find for requested icon", pe_exception::no_icon_group_found);
+}
+
+//Returns single cursor data by ID and language (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_single_cursor_by_id_lang(uint32_t language, uint32_t id) const
+{
+	std::string raw_cursor_data(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor, id).get_data());
+	//Get cursor headers
+	std::string cursor_data(lookup_cursor_group_data_by_cursor(id, language, raw_cursor_data));
+	//Append cursor data
+	cursor_data.append(raw_cursor_data.substr(sizeof(uint16_t) * 2 /* hotspot position */));
+	return cursor_data;
+}
+
+//Returns single cursor data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_single_cursor_by_id(uint32_t id, uint32_t index) const
+{
+	pe_resource_viewer::resource_language_list languages(res_.list_resource_languages(pe_resource_viewer::resource_cursor, id));
+	if(languages.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+	
+	std::string raw_cursor_data(res_.get_resource_data_by_id(pe_resource_viewer::resource_cursor, id, index).get_data());
+	//Get cursor headers
+	std::string cursor_data(lookup_cursor_group_data_by_cursor(id, languages.at(index), raw_cursor_data));
+	//Append cursor data
+	cursor_data.append(raw_cursor_data.substr(sizeof(uint16_t) * 2 /* hotspot position */));
+	return cursor_data;
+}
+
+//Helper function of creating cursor headers
+//Returns cursor count
+uint16_t resource_cursor_icon_reader::format_cursor_headers(std::string& cur_data, const std::string& resource_data, uint32_t language, uint32_t index) const
+{
+	//Check resource data length
+	if(resource_data.length() < sizeof(cursor_header))
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	const cursor_header* info = reinterpret_cast<const cursor_header*>(resource_data.data());
+
+	//Check resource data length
+	if(resource_data.length() < sizeof(cursor_header) + sizeof(cursor_group) * info->Count)
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	//Reserve needed space to speed up a little
+	cur_data.reserve(sizeof(cursor_header) + info->Count * sizeof(cursordirentry));
+	//Add cursor header
+	cur_data.append(reinterpret_cast<const char*>(info), sizeof(cursor_header));
+
+	//Iterate over all cursors listed in cursor group
+	uint32_t offset = sizeof(cursor_header) + sizeof(cursordirentry) * info->Count;
+	for(uint16_t i = 0; i != info->Count; ++i)
+	{
+		const cursor_group* group = reinterpret_cast<const cursor_group*>(resource_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+
+		//Fill cursor info
+		cursordirentry direntry;
+		direntry.ColorCount = 0; //OK
+		direntry.Width = static_cast<uint8_t>(group->Width);
+		direntry.Height = static_cast<uint8_t>(group->Height)  / 2;
+		direntry.Reserved = 0;
+
+		//Now read hotspot data from cursor data directory
+		const std::string cursor = index == 0xFFFFFFFF
+			? res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor, group->Number).get_data()
+			: res_.get_resource_data_by_id(pe_resource_viewer::resource_cursor, group->Number, index).get_data();
+		if(cursor.length() < 2 * sizeof(uint16_t))
+			throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+		//Here it is - two words in the very beginning of cursor data
+		direntry.HotspotX = *reinterpret_cast<const uint16_t*>(cursor.data());
+		direntry.HotspotY = *reinterpret_cast<const uint16_t*>(cursor.data() + sizeof(uint16_t));
+
+		//Fill the rest data
+		direntry.SizeInBytes = group->SizeInBytes - 2 * sizeof(uint16_t);
+		direntry.ImageOffset = offset;
+
+		//Add cursor header
+		cur_data.append(reinterpret_cast<const char*>(&direntry), sizeof(cursordirentry));
+
+		offset += direntry.SizeInBytes;
+	}
+
+	//Return cursor count
+	return info->Count;
+}
+
+//Returns cursor data by name and language (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_cursor_by_name(uint32_t language, const std::wstring& name) const
+{
+	std::string ret;
+
+	//Get resource by name and language
+	const std::string resource_data = res_.get_resource_data_by_name(language, pe_resource_viewer::resource_cursor_group, name).get_data();
+
+	//Create cursor headers
+	uint16_t cursor_count = format_cursor_headers(ret, resource_data, language);
+
+	//Add cursor data
+	for(uint16_t i = 0; i != cursor_count; ++i)
+	{
+		const cursor_group* group = reinterpret_cast<const cursor_group*>(resource_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+		ret += res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor, group->Number).get_data().substr(2 * sizeof(uint16_t));
+	}
+
+	return ret;
+}
+
+//Returns cursor data by name and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_cursor_by_name(const std::wstring& name, uint32_t index) const
+{
+	std::string ret;
+
+	//Get resource by name and index
+	const std::string resource_data = res_.get_resource_data_by_name(pe_resource_viewer::resource_cursor_group, name, index).get_data();
+
+	//Create cursor headers
+	uint16_t cursor_count = format_cursor_headers(ret, resource_data, 0, index);
+
+	//Add cursor data
+	for(uint16_t i = 0; i != cursor_count; ++i)
+	{
+		const cursor_group* group = reinterpret_cast<const cursor_group*>(resource_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+		ret += res_.get_resource_data_by_id(pe_resource_viewer::resource_cursor, group->Number, index).get_data().substr(2 * sizeof(uint16_t));
+	}
+
+	return ret;
+}
+
+//Returns cursor data by ID and language (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_cursor_by_id_lang(uint32_t language, uint32_t id) const
+{
+	std::string ret;
+
+	//Get resource by ID and language
+	const std::string resource_data = res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor_group, id).get_data();
+
+	//Create cursor headers
+	uint16_t cursor_count = format_cursor_headers(ret, resource_data, language);
+
+	//Add cursor data
+	for(uint16_t i = 0; i != cursor_count; ++i)
+	{
+		const cursor_group* group = reinterpret_cast<const cursor_group*>(resource_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+		ret += res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor, group->Number).get_data().substr(2 * sizeof(uint16_t));
+	}
+
+	return ret;
+}
+
+//Returns cursor data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+const std::string resource_cursor_icon_reader::get_cursor_by_id(uint32_t id, uint32_t index) const
+{
+	std::string ret;
+
+	//Get resource by ID and index
+	const std::string resource_data = res_.get_resource_data_by_id(pe_resource_viewer::resource_cursor_group, id, index).get_data();
+
+	//Create cursor headers
+	uint16_t cursor_count = format_cursor_headers(ret, resource_data, 0, index);
+
+	//Add cursor data
+	for(uint16_t i = 0; i != cursor_count; ++i)
+	{
+		const cursor_group* group = reinterpret_cast<const cursor_group*>(resource_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+		ret += res_.get_resource_data_by_id(pe_resource_viewer::resource_cursor, group->Number, index).get_data().substr(2 * sizeof(uint16_t));
+	}
+
+	return ret;
+}
+
+//Checks for cursor presence inside cursor group, fills cursor headers if found
+bool resource_cursor_icon_reader::check_cursor_presence(const std::string& cursor_group_resource_data, uint32_t cursor_id, std::string& cur_header_data, const std::string& raw_cursor_data)
+{
+	//Check resource data length
+	if(cursor_group_resource_data.length() < sizeof(cursor_header))
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	const cursor_header* info = reinterpret_cast<const cursor_header*>(cursor_group_resource_data.data());
+
+	//Check resource data length
+	if(cursor_group_resource_data.length() < sizeof(cursor_header) + sizeof(cursor_group))
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	//Iterate over all cursors listed in cursor group
+	for(uint16_t i = 0; i != info->Count; ++i)
+	{
+		const cursor_group* group = reinterpret_cast<const cursor_group*>(cursor_group_resource_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+
+		if(group->Number == cursor_id)
+		{
+			//Reserve needed space to speed up a little
+			cur_header_data.reserve(sizeof(cursor_header) + sizeof(cursordirentry));
+			//Write single-cursor cursor header
+			cursor_header new_header = *info;
+			new_header.Count = 1;
+			cur_header_data.append(reinterpret_cast<const char*>(&new_header), sizeof(cursor_header));
+
+			//Fill cursor info
+			cursordirentry direntry;
+			direntry.ColorCount = 0; //OK
+			direntry.Width = static_cast<uint8_t>(group->Width);
+			direntry.Height = static_cast<uint8_t>(group->Height)  / 2;
+			direntry.Reserved = 0;
+
+			if(raw_cursor_data.length() < 2 * sizeof(uint16_t))
+				throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+			//Here it is - two words in the very beginning of cursor data
+			direntry.HotspotX = *reinterpret_cast<const uint16_t*>(raw_cursor_data.data());
+			direntry.HotspotY = *reinterpret_cast<const uint16_t*>(raw_cursor_data.data() + sizeof(uint16_t));
+
+			//Fill the rest data
+			direntry.SizeInBytes = group->SizeInBytes - 2 * sizeof(uint16_t);
+			direntry.ImageOffset = sizeof(cursor_header) + sizeof(cursordirentry);
+
+			//Add cursor header
+			cur_header_data.append(reinterpret_cast<const char*>(&direntry), sizeof(cursordirentry));
+
+			return true;
+		}
+	}
+
+	return false;
+}
+
+//Looks up cursor group by cursor id and returns full cursor headers if found
+const std::string resource_cursor_icon_reader::lookup_cursor_group_data_by_cursor(uint32_t cursor_id, uint32_t language, const std::string& raw_cursor_data) const
+{
+	std::string cursor_header_data;
+
+	{
+		//List all ID-resources
+		pe_resource_viewer::resource_id_list ids(res_.list_resource_ids(pe_resource_viewer::resource_cursor_group));
+
+		for(pe_resource_viewer::resource_id_list::const_iterator it = ids.begin(); it != ids.end(); ++it)
+		{
+			pe_resource_viewer::resource_language_list group_languages(res_.list_resource_languages(pe_resource_viewer::resource_cursor_group, *it));
+			if(std::find(group_languages.begin(), group_languages.end(), language) != group_languages.end()
+				&& check_cursor_presence(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor_group, *it).get_data(), cursor_id, cursor_header_data, raw_cursor_data))
+				return cursor_header_data;
+		}
+	}
+
+	{
+		//List all named resources
+		pe_resource_viewer::resource_name_list names(res_.list_resource_names(pe_resource_viewer::resource_cursor_group));
+		for(pe_resource_viewer::resource_name_list::const_iterator it = names.begin(); it != names.end(); ++it)
+		{
+			pe_resource_viewer::resource_language_list group_languages(res_.list_resource_languages(pe_resource_viewer::resource_cursor_group, *it));
+			if(std::find(group_languages.begin(), group_languages.end(), language) != group_languages.end()
+				&& check_cursor_presence(res_.get_resource_data_by_name(language, pe_resource_viewer::resource_cursor_group, *it).get_data(), cursor_id, cursor_header_data, raw_cursor_data))
+				return cursor_header_data;
+		}
+	}
+
+	throw pe_exception("No cursor group find for requested icon", pe_exception::no_cursor_group_found);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_reader.h b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_reader.h
new file mode 100644
index 0000000000000000000000000000000000000000..7dd1baae1be85e06d74c95cecaf53a862e2bb9a4
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_reader.h
@@ -0,0 +1,66 @@
+#ifndef pebliss_resource_cursor_icon_reader_h
+#define pebliss_resource_cursor_icon_reader_h
+#pragma once
+#include <string>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+class pe_resource_viewer;
+
+class resource_cursor_icon_reader
+{
+public:
+	resource_cursor_icon_reader(const pe_resource_viewer& res);
+
+	//Returns single icon data by ID and language (minimum checks of format correctness)
+	const std::string get_single_icon_by_id_lang(uint32_t language, uint32_t id) const;
+	//Returns single icon data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_single_icon_by_id(uint32_t id, uint32_t index = 0) const;
+
+	//Returns icon data of group of icons by name and language (minimum checks of format correctness)
+	const std::string get_icon_by_name(uint32_t language, const std::wstring& icon_group_name) const;
+	//Returns icon data of group of icons by name and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_icon_by_name(const std::wstring& icon_group_name, uint32_t index = 0) const;
+	//Returns icon data of group of icons by ID and language (minimum checks of format correctness)
+	const std::string get_icon_by_id_lang(uint32_t language, uint32_t icon_group_id) const;
+	//Returns icon data of group of icons by ID and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_icon_by_id(uint32_t icon_group_id, uint32_t index = 0) const;
+	
+	//Returns single cursor data by ID and language (minimum checks of format correctness)
+	const std::string get_single_cursor_by_id_lang(uint32_t language, uint32_t id) const;
+	//Returns single cursor data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_single_cursor_by_id(uint32_t id, uint32_t index = 0) const;
+
+	//Returns cursor data by name and language (minimum checks of format correctness)
+	const std::string get_cursor_by_name(uint32_t language, const std::wstring& cursor_group_name) const;
+	//Returns cursor data by name and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_cursor_by_name(const std::wstring& cursor_group_name, uint32_t index = 0) const;
+	//Returns cursor data by ID and language (minimum checks of format correctness)
+	const std::string get_cursor_by_id_lang(uint32_t language, uint32_t cursor_group_id) const;
+	//Returns cursor data by ID and index in language directory (instead of language) (minimum checks of format correctness)
+	const std::string get_cursor_by_id(uint32_t cursor_group_id, uint32_t index = 0) const;
+
+private:
+	const pe_resource_viewer& res_;
+
+	//Helper function of creating icon headers from ICON_GROUP resource data
+	//Returns icon count
+	static uint16_t format_icon_headers(std::string& ico_data, const std::string& resource_data);
+	
+	//Helper function of creating cursor headers from CURSOR_GROUP resource data
+	//Returns cursor count
+	uint16_t format_cursor_headers(std::string& cur_data, const std::string& resource_data, uint32_t language, uint32_t index = 0xFFFFFFFF) const;
+
+	//Looks up icon group by icon id and returns full icon headers if found
+	const std::string lookup_icon_group_data_by_icon(uint32_t icon_id, uint32_t language) const;
+	//Checks for icon presence inside icon group, fills icon headers if found
+	static bool check_icon_presence(const std::string& icon_group_resource_data, uint32_t icon_id, std::string& ico_data);
+
+	//Looks up cursor group by cursor id and returns full cursor headers if found
+	const std::string lookup_cursor_group_data_by_cursor(uint32_t cursor_id, uint32_t language, const std::string& raw_cursor_data) const;
+	//Checks for cursor presence inside cursor group, fills cursor headers if found
+	static bool check_cursor_presence(const std::string& icon_group_resource_data, uint32_t cursor_id, std::string& cur_header_data, const std::string& raw_cursor_data);
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_writer.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_writer.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ce52c6cbdfaf4ffe489ca2f07691f605d16f9090
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_writer.cpp
@@ -0,0 +1,426 @@
+#include <algorithm>
+#include <string.h>
+#include "resource_cursor_icon_writer.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+resource_cursor_icon_writer::resource_cursor_icon_writer(pe_resource_manager& res)
+	:res_(res)
+{}
+
+//Add icon helper
+void resource_cursor_icon_writer::add_icon(const std::string& icon_file, const resource_data_info* group_icon_info /* or zero */, resource_directory_entry& new_icon_group_entry, const resource_directory::entry_finder& finder, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp)
+{
+	//Check icon for correctness
+	if(icon_file.length() < sizeof(ico_header))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	const ico_header* icon_header = reinterpret_cast<const ico_header*>(&icon_file[0]);
+
+	unsigned long size_of_headers = sizeof(ico_header) + icon_header->Count * sizeof(icondirentry);
+	if(icon_file.length() < size_of_headers || icon_header->Count == 0)
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	//Enumerate all icons in file
+	for(uint16_t i = 0; i != icon_header->Count; ++i)
+	{
+		//Check icon entries
+		const icondirentry* icon_entry = reinterpret_cast<const icondirentry*>(&icon_file[sizeof(ico_header) + i * sizeof(icondirentry)]);
+		if(icon_entry->SizeInBytes == 0
+			|| icon_entry->ImageOffset < size_of_headers
+			|| !pe_utils::is_sum_safe(icon_entry->ImageOffset, icon_entry->SizeInBytes)
+			|| icon_entry->ImageOffset + icon_entry->SizeInBytes > icon_file.length())
+			throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+	}
+
+	std::string icon_group_data;
+	ico_header* info = 0;
+
+	if(group_icon_info)
+	{
+		//If icon group already exists
+		{
+			icon_group_data = group_icon_info->get_data();
+			codepage = group_icon_info->get_codepage(); //Don't change codepage of icon group entry
+		}
+
+		//Check resource data size
+		if(icon_group_data.length() < sizeof(ico_header))
+			throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+		//Get icon header
+		info = reinterpret_cast<ico_header*>(&icon_group_data[0]);
+
+		//Check resource data size
+		if(icon_group_data.length() < sizeof(ico_header) + info->Count * sizeof(icon_group))
+			throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+		icon_group_data.resize(sizeof(ico_header) + (info->Count + icon_header->Count) * sizeof(icon_group));
+		info = reinterpret_cast<ico_header*>(&icon_group_data[0]); //In case if memory was reallocated
+	}
+	else //Entry not found - icon group doesn't exist
+	{
+		icon_group_data.resize(sizeof(ico_header) + icon_header->Count * sizeof(icon_group));
+		memcpy(&icon_group_data[0], icon_header, sizeof(ico_header));
+	}
+
+	//Search for available icon IDs
+	std::vector<uint16_t> icon_id_list(get_icon_or_cursor_free_id_list(pe_resource_viewer::resource_icon, mode, icon_header->Count));
+
+	//Enumerate all icons in file
+	for(uint16_t i = 0; i != icon_header->Count; ++i)
+	{
+		const icondirentry* icon_entry = reinterpret_cast<const icondirentry*>(&icon_file[sizeof(ico_header) + i * sizeof(icondirentry)]);
+		icon_group group = {0};
+
+		//Fill icon resource header
+		group.BitCount = icon_entry->BitCount;
+		group.ColorCount = icon_entry->ColorCount;
+		group.Height = icon_entry->Height;
+		group.Planes = icon_entry->Planes;
+		group.Reserved = icon_entry->Reserved;
+		group.SizeInBytes = icon_entry->SizeInBytes;
+		group.Width = icon_entry->Width;
+		group.Number = icon_id_list.at(i);
+
+		memcpy(&icon_group_data[sizeof(ico_header) + ((info ? info->Count : 0) + i) * sizeof(icon_group)], &group, sizeof(group));
+
+		//Add icon to resources
+		resource_directory_entry new_entry;
+		new_entry.set_id(group.Number);
+		res_.add_resource(icon_file.substr(icon_entry->ImageOffset, icon_entry->SizeInBytes), pe_resource_viewer::resource_icon, new_entry, resource_directory::entry_finder(group.Number), language, codepage, timestamp);
+	}
+
+	if(info)
+		info->Count += icon_header->Count; //Increase icon count, if we're adding icon to existing group
+
+	{
+		//Add or replace icon group data entry
+		res_.add_resource(icon_group_data, pe_resource_viewer::resource_icon_group, new_icon_group_entry, finder, language, codepage, timestamp);
+	}
+}
+
+//Returns free icon or cursor ID list depending on icon_place_mode
+const std::vector<uint16_t> resource_cursor_icon_writer::get_icon_or_cursor_free_id_list(pe_resource_viewer::resource_type type, icon_place_mode mode, uint32_t count)
+{
+	//Search for available icon/cursor IDs
+	std::vector<uint16_t> icon_cursor_id_list;
+
+	try
+	{
+		//If any icon exists
+		//List icon IDs
+		std::vector<uint32_t> id_list(res_.list_resource_ids(type));
+		std::sort(id_list.begin(), id_list.end());
+
+		//If we are placing icon on free spaces
+		//I.e., icon IDs 1, 3, 4, 7, 8 already exist
+		//We'll place five icons on IDs 2, 5, 6, 9, 10
+		if(mode != icon_place_after_max_icon_id)
+		{
+			if(!id_list.empty())
+			{
+				//Determine and list free icon IDs
+				for(std::vector<uint32_t>::const_iterator it = id_list.begin(); it != id_list.end(); ++it)
+				{
+					if(it == id_list.begin())
+					{
+						if(*it > 1)
+						{
+							for(uint16_t i = 1; i != *it; ++i)
+							{
+								icon_cursor_id_list.push_back(i);
+								if(icon_cursor_id_list.size() == count)
+									break;
+							}
+						}
+					}
+					else if(*(it - 1) - *it > 1)
+					{
+						for(uint16_t i = static_cast<uint16_t>(*(it - 1) + 1); i != static_cast<uint16_t>(*it); ++i)
+						{
+							icon_cursor_id_list.push_back(i);
+							if(icon_cursor_id_list.size() == count)
+								break;
+						}
+					}
+
+					if(icon_cursor_id_list.size() == count)
+						break;
+				}
+			}
+		}
+
+		uint32_t max_id = id_list.empty() ? 0 : *std::max_element(id_list.begin(), id_list.end());
+		for(uint32_t i = static_cast<uint32_t>(icon_cursor_id_list.size()); i != count; ++i)
+			icon_cursor_id_list.push_back(static_cast<uint16_t>(++max_id));
+	}
+	catch(const pe_exception&) //Entry not found
+	{
+		for(uint16_t i = 1; i != count + 1; ++i)
+			icon_cursor_id_list.push_back(i);
+	}
+
+	return icon_cursor_id_list;
+}
+
+//Add cursor helper
+void resource_cursor_icon_writer::add_cursor(const std::string& cursor_file, const resource_data_info* group_cursor_info /* or zero */, resource_directory_entry& new_cursor_group_entry, const resource_directory::entry_finder& finder, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp)
+{
+	//Check cursor for correctness
+	if(cursor_file.length() < sizeof(cursor_header))
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	const cursor_header* cur_header = reinterpret_cast<const cursor_header*>(&cursor_file[0]);
+
+	unsigned long size_of_headers = sizeof(cursor_header) + cur_header->Count * sizeof(cursordirentry);
+	if(cursor_file.length() < size_of_headers || cur_header->Count == 0)
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	//Enumerate all cursors in file
+	for(uint16_t i = 0; i != cur_header->Count; ++i)
+	{
+		//Check cursor entries
+		const cursordirentry* cursor_entry = reinterpret_cast<const cursordirentry*>(&cursor_file[sizeof(cursor_header) + i * sizeof(cursordirentry)]);
+		if(cursor_entry->SizeInBytes == 0
+			|| cursor_entry->ImageOffset < size_of_headers
+			|| !pe_utils::is_sum_safe(cursor_entry->ImageOffset, cursor_entry->SizeInBytes)
+			|| cursor_entry->ImageOffset + cursor_entry->SizeInBytes > cursor_file.length())
+			throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+	}
+
+	std::string cursor_group_data;
+	cursor_header* info = 0;
+
+	if(group_cursor_info)
+	{
+		//If cursor group already exists
+		{
+			cursor_group_data = group_cursor_info->get_data();
+			codepage = group_cursor_info->get_codepage(); //Don't change codepage of cursor group entry
+		}
+
+		//Check resource data size
+		if(cursor_group_data.length() < sizeof(cursor_header))
+			throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+		//Get cursor header
+		info = reinterpret_cast<cursor_header*>(&cursor_group_data[0]);
+
+		//Check resource data size
+		if(cursor_group_data.length() < sizeof(cursor_header) + info->Count * sizeof(cursor_group))
+			throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+		cursor_group_data.resize(sizeof(cursor_header) + (info->Count + cur_header->Count) * sizeof(cursor_group));
+		info = reinterpret_cast<cursor_header*>(&cursor_group_data[0]); //In case if memory was reallocated
+	}
+	else //Entry not found - cursor group doesn't exist
+	{
+		cursor_group_data.resize(sizeof(cursor_header) + cur_header->Count * sizeof(cursor_group));
+		memcpy(&cursor_group_data[0], cur_header, sizeof(cursor_header));
+	}
+
+	//Search for available cursor IDs
+	std::vector<uint16_t> cursor_id_list(get_icon_or_cursor_free_id_list(pe_resource_viewer::resource_cursor, mode, cur_header->Count));
+
+	//Enumerate all cursors in file
+	for(uint16_t i = 0; i != cur_header->Count; ++i)
+	{
+		const cursordirentry* cursor_entry = reinterpret_cast<const cursordirentry*>(&cursor_file[sizeof(cursor_header) + i * sizeof(cursordirentry)]);
+		cursor_group group = {0};
+
+		//Fill cursor resource header
+		group.Height = cursor_entry->Height * 2;
+		group.SizeInBytes = cursor_entry->SizeInBytes + 2 * sizeof(uint16_t) /* hotspot coordinates */;
+		group.Width = cursor_entry->Width;
+		group.Number = cursor_id_list.at(i);
+
+		memcpy(&cursor_group_data[sizeof(cursor_header) + ((info ? info->Count : 0) + i) * sizeof(cursor_group)], &group, sizeof(group));
+
+		//Add cursor to resources
+		resource_directory_entry new_entry;
+		new_entry.set_id(group.Number);
+
+		//Fill resource data (two WORDs for hotspot of cursor, and cursor bitmap data)
+		std::string cur_data;
+		cur_data.resize(sizeof(uint16_t) * 2);
+		memcpy(&cur_data[0], &cursor_entry->HotspotX, sizeof(uint16_t));
+		memcpy(&cur_data[sizeof(uint16_t)], &cursor_entry->HotspotY, sizeof(uint16_t));
+		cur_data.append(cursor_file.substr(cursor_entry->ImageOffset, cursor_entry->SizeInBytes));
+
+		res_.add_resource(cur_data, pe_resource_viewer::resource_cursor, new_entry, resource_directory::entry_finder(group.Number), language, codepage, timestamp);
+	}
+
+	if(info)
+		info->Count += cur_header->Count; //Increase cursor count, if we're adding cursor to existing group
+
+	{
+		//Add or replace cursor group data entry
+		res_.add_resource(cursor_group_data, pe_resource_viewer::resource_cursor_group, new_cursor_group_entry, finder, language, codepage, timestamp);
+	}
+}
+
+//Adds icon(s) from icon file data
+//timestamp will be used for directories that will be added
+//If icon group with name "icon_group_name" or ID "icon_group_id" already exists, it will be appended with new icon(s)
+//(Codepage of icon group and icons will not be changed in this case)
+//icon_place_mode determines, how new icon(s) will be placed
+void resource_cursor_icon_writer::add_icon(const std::string& icon_file, const std::wstring& icon_group_name, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_icon_group_entry;
+	new_icon_group_entry.set_name(icon_group_name);
+	std::auto_ptr<resource_data_info> data_info;
+
+	try
+	{
+		data_info.reset(new resource_data_info(res_.get_resource_data_by_name(language, pe_resource_viewer::resource_icon_group, icon_group_name)));
+	}
+	catch(const pe_exception&) //Entry not found
+	{
+	}
+
+	add_icon(icon_file, data_info.get(), new_icon_group_entry, resource_directory::entry_finder(icon_group_name), language, mode, codepage, timestamp);
+}
+
+void resource_cursor_icon_writer::add_icon(const std::string& icon_file, uint32_t icon_group_id, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_icon_group_entry;
+	new_icon_group_entry.set_id(icon_group_id);
+	std::auto_ptr<resource_data_info> data_info;
+
+	try
+	{
+		data_info.reset(new resource_data_info(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon_group, icon_group_id)));
+	}
+	catch(const pe_exception&) //Entry not found
+	{
+	}
+
+	add_icon(icon_file, data_info.get(), new_icon_group_entry, resource_directory::entry_finder(icon_group_id), language, mode, codepage, timestamp);
+}
+
+//Adds cursor(s) from cursor file data
+//timestamp will be used for directories that will be added
+//If cursor group with name "cursor_group_name" or ID "cursor_group_id" already exists, it will be appended with new cursor(s)
+//(Codepage of cursor group and cursors will not be changed in this case)
+//icon_place_mode determines, how new cursor(s) will be placed
+void resource_cursor_icon_writer::add_cursor(const std::string& cursor_file, const std::wstring& cursor_group_name, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_cursor_group_entry;
+	new_cursor_group_entry.set_name(cursor_group_name);
+	std::auto_ptr<resource_data_info> data_info;
+
+	try
+	{
+		data_info.reset(new resource_data_info(res_.get_resource_data_by_name(language, pe_resource_viewer::resource_cursor_group, cursor_group_name)));
+	}
+	catch(const pe_exception&) //Entry not found
+	{
+	}
+
+	add_cursor(cursor_file, data_info.get(), new_cursor_group_entry, resource_directory::entry_finder(cursor_group_name), language, mode, codepage, timestamp);
+}
+
+void resource_cursor_icon_writer::add_cursor(const std::string& cursor_file, uint32_t cursor_group_id, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp)
+{
+	resource_directory_entry new_cursor_group_entry;
+	new_cursor_group_entry.set_id(cursor_group_id);
+	std::auto_ptr<resource_data_info> data_info;
+
+	try
+	{
+		data_info.reset(new resource_data_info(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor_group, cursor_group_id)));
+	}
+	catch(const pe_exception&) //Entry not found
+	{
+	}
+
+	add_cursor(cursor_file, data_info.get(), new_cursor_group_entry, resource_directory::entry_finder(cursor_group_id), language, mode, codepage, timestamp);
+}
+
+//Remove icon group helper
+void resource_cursor_icon_writer::remove_icons_from_icon_group(const std::string& icon_group_data, uint32_t language)
+{
+	//Check resource data size
+	if(icon_group_data.length() < sizeof(ico_header))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	//Get icon header
+	const ico_header* info = reinterpret_cast<const ico_header*>(icon_group_data.data());
+
+	uint16_t icon_count = info->Count;
+
+	//Check resource data size
+	if(icon_group_data.length() < sizeof(ico_header) + icon_count * sizeof(icon_group))
+		throw pe_exception("Incorrect resource icon", pe_exception::resource_incorrect_icon);
+
+	//Remove icon data
+	for(uint16_t i = 0; i != icon_count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(icon_group_data.data() + sizeof(ico_header) + i * sizeof(icon_group));
+		res_.remove_resource(pe_resource_viewer::resource_icon, group->Number, language);
+	}
+}
+
+//Remove cursor group helper
+void resource_cursor_icon_writer::remove_cursors_from_cursor_group(const std::string& cursor_group_data, uint32_t language)
+{
+	//Check resource data size
+	if(cursor_group_data.length() < sizeof(cursor_header))
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	//Get icon header
+	const cursor_header* info = reinterpret_cast<const cursor_header*>(cursor_group_data.data());
+
+	uint16_t cursor_count = info->Count;
+
+	//Check resource data size
+	if(cursor_group_data.length() < sizeof(cursor_header) + cursor_count * sizeof(cursor_group))
+		throw pe_exception("Incorrect resource cursor", pe_exception::resource_incorrect_cursor);
+
+	//Remove icon data
+	for(uint16_t i = 0; i != cursor_count; ++i)
+	{
+		const icon_group* group = reinterpret_cast<const icon_group*>(cursor_group_data.data() + sizeof(cursor_header) + i * sizeof(cursor_group));
+		res_.remove_resource(pe_resource_viewer::resource_cursor, group->Number, language);
+	}
+}
+
+//Removes cursor group and all its cursors by name/ID and language
+bool resource_cursor_icon_writer::remove_cursor_group(const std::wstring& cursor_group_name, uint32_t language)
+{
+	//Get resource by name and language
+	const std::string data = res_.get_resource_data_by_name(language, pe_resource_viewer::resource_cursor_group, cursor_group_name).get_data();
+	remove_cursors_from_cursor_group(data, language);
+	return res_.remove_resource(pe_resource_viewer::resource_cursor_group, cursor_group_name, language);
+}
+
+//Removes cursor group and all its cursors by name/ID and language
+bool resource_cursor_icon_writer::remove_cursor_group(uint32_t cursor_group_id, uint32_t language)
+{
+	//Get resource by name and language
+	const std::string data = res_.get_resource_data_by_id(language, pe_resource_viewer::resource_cursor_group, cursor_group_id).get_data();
+	remove_cursors_from_cursor_group(data, language);
+	return res_.remove_resource(pe_resource_viewer::resource_cursor_group, cursor_group_id, language);
+}
+
+//Removes icon group and all its icons by name/ID and language
+bool resource_cursor_icon_writer::remove_icon_group(const std::wstring& icon_group_name, uint32_t language)
+{
+	//Get resource by name and language
+	const std::string data = res_.get_resource_data_by_name(language, pe_resource_viewer::resource_icon_group, icon_group_name).get_data();
+	remove_icons_from_icon_group(data, language);
+	return res_.remove_resource(pe_resource_viewer::resource_icon_group, icon_group_name, language);
+}
+
+//Removes icon group and all its icons by name/ID and language
+bool resource_cursor_icon_writer::remove_icon_group(uint32_t icon_group_id, uint32_t language)
+{
+	//Get resource by name and language
+	const std::string data = res_.get_resource_data_by_id(language, pe_resource_viewer::resource_icon_group, icon_group_id).get_data();
+	remove_icons_from_icon_group(data, language);
+	return res_.remove_resource(pe_resource_viewer::resource_icon_group, icon_group_id, language);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_writer.h b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_writer.h
new file mode 100644
index 0000000000000000000000000000000000000000..726826a37d801b0e4924d7713a413aa6b45bc122
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_cursor_icon_writer.h
@@ -0,0 +1,76 @@
+#ifndef pebliss_resource_cursor_icon_writer_h
+#define pebliss_resource_cursor_icon_writer_h
+#pragma once
+#include <string>
+#include <vector>
+#include "stdint_defs.h"
+#include "pe_resource_manager.h"
+
+namespace pe_bliss
+{
+class pe_resource_manager;
+
+class resource_cursor_icon_writer
+{
+public:
+	//Determines, how new icon(s) or cursor(s) will be placed
+	enum icon_place_mode
+	{
+		icon_place_after_max_icon_id, //Icon(s) will be placed after all existing
+		icon_place_free_ids //New icon(s) will take all free IDs between existing icons
+	};
+	
+public:
+	resource_cursor_icon_writer(pe_resource_manager& res);
+
+	//Removes icon group and all its icons by name/ID and language
+	bool remove_icon_group(const std::wstring& icon_group_name, uint32_t language);
+	bool remove_icon_group(uint32_t icon_group_id, uint32_t language);
+
+	//Adds icon(s) from icon file data
+	//timestamp will be used for directories that will be added
+	//If icon group with name "icon_group_name" or ID "icon_group_id" already exists, it will be appended with new icon(s)
+	//(Codepage of icon group and icons will not be changed in this case)
+	//icon_place_mode determines, how new icon(s) will be placed
+	void add_icon(const std::string& icon_file,
+		const std::wstring& icon_group_name,
+		uint32_t language, icon_place_mode mode = icon_place_after_max_icon_id,
+		uint32_t codepage = 0, uint32_t timestamp = 0);
+
+	void add_icon(const std::string& icon_file,
+		uint32_t icon_group_id,
+		uint32_t language, icon_place_mode mode = icon_place_after_max_icon_id,
+		uint32_t codepage = 0, uint32_t timestamp = 0);
+	
+	//Removes cursor group and all its cursors by name/ID and language
+	bool remove_cursor_group(const std::wstring& cursor_group_name, uint32_t language);
+	bool remove_cursor_group(uint32_t cursor_group_id, uint32_t language);
+
+	//Adds cursor(s) from cursor file data
+	//timestamp will be used for directories that will be added
+	//If cursor group with name "cursor_group_name" or ID "cursor_group_id" already exists, it will be appended with new cursor(s)
+	//(Codepage of cursor group and cursors will not be changed in this case)
+	//icon_place_mode determines, how new cursor(s) will be placed
+	void add_cursor(const std::string& cursor_file, const std::wstring& cursor_group_name, uint32_t language, icon_place_mode mode = icon_place_after_max_icon_id, uint32_t codepage = 0, uint32_t timestamp = 0);
+	void add_cursor(const std::string& cursor_file, uint32_t cursor_group_id, uint32_t language, icon_place_mode mode = icon_place_after_max_icon_id, uint32_t codepage = 0, uint32_t timestamp = 0);
+
+private:
+	pe_resource_manager& res_;
+
+	//Add icon helper
+	void add_icon(const std::string& icon_file, const resource_data_info* group_icon_info /* or zero */, resource_directory_entry& new_icon_group_entry, const resource_directory::entry_finder& finder, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp);
+	
+	//Remove icon group helper
+	void remove_icons_from_icon_group(const std::string& icon_group_data, uint32_t language);
+
+	//Add cursor helper
+	void add_cursor(const std::string& cursor_file, const resource_data_info* group_cursor_info /* or zero */, resource_directory_entry& new_cursor_group_entry, const resource_directory::entry_finder& finder, uint32_t language, icon_place_mode mode, uint32_t codepage, uint32_t timestamp);
+
+	//Remove cursor group helper
+	void remove_cursors_from_cursor_group(const std::string& cursor_group_data, uint32_t language);
+
+	//Returns free icon or cursor ID list depending on icon_place_mode
+	const std::vector<uint16_t> get_icon_or_cursor_free_id_list(pe_resource_manager::resource_type type, icon_place_mode mode, uint32_t count);
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_data_info.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_data_info.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..bc7b3abd7dd1f533ca45c708edfd50969413abfe
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_data_info.cpp
@@ -0,0 +1,27 @@
+#include "resource_data_info.h"
+#include "pe_resource_viewer.h"
+
+namespace pe_bliss
+{
+//Default constructor
+resource_data_info::resource_data_info(const std::string& data, uint32_t codepage)
+	:data_(data), codepage_(codepage)
+{}
+
+//Constructor from data
+resource_data_info::resource_data_info(const resource_data_entry& data)
+	:data_(data.get_data()), codepage_(data.get_codepage())
+{}
+
+//Returns resource data
+const std::string& resource_data_info::get_data() const
+{
+	return data_;
+}
+
+//Returns resource codepage
+uint32_t resource_data_info::get_codepage() const
+{
+	return codepage_;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_data_info.h b/irdb-lib/pebliss/trunk/pe_lib/resource_data_info.h
new file mode 100644
index 0000000000000000000000000000000000000000..501036387cebacf89076292579a4dd0991227ac2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_data_info.h
@@ -0,0 +1,30 @@
+#ifndef pebliss_resource_data_info_h
+#define pebliss_resource_data_info_h
+#pragma once
+#include <string>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+class resource_data_entry;
+
+//Class representing resource data
+class resource_data_info
+{
+public:
+	//Constructor from data
+	resource_data_info(const std::string& data, uint32_t codepage);
+	//Constructor from data
+	explicit resource_data_info(const resource_data_entry& data);
+
+	//Returns resource data
+	const std::string& get_data() const;
+	//Returns resource codepage
+	uint32_t get_codepage() const;
+
+private:
+	std::string data_;
+	uint32_t codepage_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_internal.h b/irdb-lib/pebliss/trunk/pe_lib/resource_internal.h
new file mode 100644
index 0000000000000000000000000000000000000000..ecb8aa0be3dfdcf67490a17c5b8f949ab73f571d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_internal.h
@@ -0,0 +1,16 @@
+#ifndef pebliss_resource_internal_h
+#define pebliss_resource_internal_h
+#pragma once
+
+#define U16TEXT(t) reinterpret_cast<const unicode16_t*>( t )
+
+#define StringFileInfo U16TEXT("S\0t\0r\0i\0n\0g\0F\0i\0l\0e\0I\0n\0f\0o\0\0")
+#define SizeofStringFileInfo sizeof("S\0t\0r\0i\0n\0g\0F\0i\0l\0e\0I\0n\0f\0o\0\0")
+#define VarFileInfo U16TEXT("V\0a\0r\0F\0i\0l\0e\0I\0n\0f\0o\0\0")
+#define Translation U16TEXT("T\0r\0a\0n\0s\0l\0a\0t\0i\0o\0n\0\0")
+
+#define VarFileInfoAligned U16TEXT("V\0a\0r\0F\0i\0l\0e\0I\0n\0f\0o\0\0\0\0")
+#define TranslationAligned U16TEXT("T\0r\0a\0n\0s\0l\0a\0t\0i\0o\0n\0\0\0\0")
+#define SizeofVarFileInfoAligned sizeof("V\0a\0r\0F\0i\0l\0e\0I\0n\0f\0o\0\0\0\0")
+#define SizeofTranslationAligned sizeof("T\0r\0a\0n\0s\0l\0a\0t\0i\0o\0n\0\0\0\0")
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_message_list_reader.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_message_list_reader.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ff9a5dd8610c6004ed0a59b870a1eb3eeac227b6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_message_list_reader.cpp
@@ -0,0 +1,110 @@
+#include "resource_message_list_reader.h"
+#include "pe_resource_viewer.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+resource_message_list_reader::resource_message_list_reader(const pe_resource_viewer& res)
+	:res_(res)
+{}
+
+//Helper function of parsing message list table
+const resource_message_list resource_message_list_reader::parse_message_list(const std::string& resource_data)
+{
+	resource_message_list ret;
+
+	//Check resource data length
+	if(resource_data.length() < sizeof(message_resource_data))
+		throw pe_exception("Incorrect resource message table", pe_exception::resource_incorrect_message_table);
+
+	const message_resource_data* message_data = reinterpret_cast<const message_resource_data*>(resource_data.data());
+
+	//Check resource data length more carefully and some possible overflows
+	if(message_data->NumberOfBlocks >= pe_utils::max_dword / sizeof(message_resource_block)
+		|| !pe_utils::is_sum_safe(message_data->NumberOfBlocks * sizeof(message_resource_block), sizeof(message_resource_data))
+		|| resource_data.length() < message_data->NumberOfBlocks * sizeof(message_resource_block) + sizeof(message_resource_data))
+		throw pe_exception("Incorrect resource message table", pe_exception::resource_incorrect_message_table);
+
+	//Iterate over all message resource blocks
+	for(unsigned long i = 0; i != message_data->NumberOfBlocks; ++i)
+	{
+		//Get block
+		const message_resource_block* block =
+			reinterpret_cast<const message_resource_block*>(resource_data.data() + sizeof(message_resource_data) - sizeof(message_resource_block) + sizeof(message_resource_block) * i);
+
+		//Check resource data length and IDs
+		if(resource_data.length() < block->OffsetToEntries || block->LowId > block->HighId)
+			throw pe_exception("Incorrect resource message table", pe_exception::resource_incorrect_message_table);
+
+		unsigned long current_pos = 0;
+		static const unsigned long size_of_entry_headers = 4;
+		//List all message resource entries in block
+		for(uint32_t curr_id = block->LowId; curr_id <= block->HighId; curr_id++)
+		{
+			//Check resource data length and some possible overflows
+			if(!pe_utils::is_sum_safe(block->OffsetToEntries, current_pos)
+				|| !pe_utils::is_sum_safe(block->OffsetToEntries + current_pos, size_of_entry_headers)
+				|| resource_data.length() < block->OffsetToEntries + current_pos + size_of_entry_headers)
+				throw pe_exception("Incorrect resource message table", pe_exception::resource_incorrect_message_table);
+
+			//Get entry
+			const message_resource_entry* entry = reinterpret_cast<const message_resource_entry*>(resource_data.data() + block->OffsetToEntries + current_pos);
+
+			//Check resource data length and entry length and some possible overflows
+			if(entry->Length < size_of_entry_headers
+				|| !pe_utils::is_sum_safe(block->OffsetToEntries + current_pos, entry->Length)
+				|| resource_data.length() < block->OffsetToEntries + current_pos + entry->Length
+				|| entry->Length < size_of_entry_headers)
+				throw pe_exception("Incorrect resource message table", pe_exception::resource_incorrect_message_table);
+
+			if(entry->Flags & message_resource_unicode)
+			{
+				//If string is UNICODE
+				//Check its length
+				if(entry->Length % 2)
+					throw pe_exception("Incorrect resource message table", pe_exception::resource_incorrect_message_table);
+
+				//Add ID and string to message table
+#ifdef PE_BLISS_WINDOWS
+				ret.insert(std::make_pair(curr_id, message_table_item(
+					std::wstring(reinterpret_cast<const wchar_t*>(resource_data.data() + block->OffsetToEntries + current_pos + size_of_entry_headers),
+					(entry->Length - size_of_entry_headers) / 2)
+					)));
+#else
+				ret.insert(std::make_pair(curr_id, message_table_item(
+					pe_utils::from_ucs2(u16string(reinterpret_cast<const unicode16_t*>(resource_data.data() + block->OffsetToEntries + current_pos + size_of_entry_headers),
+					(entry->Length - size_of_entry_headers) / 2))
+					)));
+#endif
+			}
+			else
+			{
+				//If string is ANSI
+				//Add ID and string to message table
+				ret.insert(std::make_pair(curr_id, message_table_item(
+					std::string(resource_data.data() + block->OffsetToEntries + current_pos + size_of_entry_headers,
+					entry->Length - size_of_entry_headers)
+					)));
+			}
+
+			//Go to next entry
+			current_pos += entry->Length;
+		}
+	}
+
+	return ret;
+}
+
+//Returns message table data by ID and index in language directory (instead of language)
+const resource_message_list resource_message_list_reader::get_message_table_by_id(uint32_t id, uint32_t index) const
+{
+	return parse_message_list(res_.get_resource_data_by_id(pe_resource_viewer::resource_message_table, id, index).get_data());
+}
+
+//Returns message table data by ID and language
+const resource_message_list resource_message_list_reader::get_message_table_by_id_lang(uint32_t language, uint32_t id) const
+{
+	return parse_message_list(res_.get_resource_data_by_id(language, pe_resource_viewer::resource_message_table, id).get_data());
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_message_list_reader.h b/irdb-lib/pebliss/trunk/pe_lib/resource_message_list_reader.h
new file mode 100644
index 0000000000000000000000000000000000000000..fdc9e194bc94298d5d65aa8e82c41c70d2b1d745
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_message_list_reader.h
@@ -0,0 +1,31 @@
+#ifndef pebliss_resource_message_list_reader_h
+#define pebliss_resource_message_list_reader_h
+#pragma once
+#include "message_table.h"
+
+namespace pe_bliss
+{
+class pe_resource_viewer;
+
+//ID; message_table_item
+typedef std::map<uint32_t, message_table_item> resource_message_list;
+
+class resource_message_list_reader
+{
+public:
+	resource_message_list_reader(const pe_resource_viewer& res);
+
+	//Returns message table data by ID and language
+	const resource_message_list get_message_table_by_id_lang(uint32_t language, uint32_t id) const;
+	//Returns message table data by ID and index in language directory (instead of language)
+	const resource_message_list get_message_table_by_id(uint32_t id, uint32_t index = 0) const;
+
+	//Helper function of parsing message list table
+	//resource_data - raw message table resource data
+	static const resource_message_list parse_message_list(const std::string& resource_data);
+
+private:
+	const pe_resource_viewer& res_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_string_table_reader.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_string_table_reader.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..33eace1935f9e4bd68685f5e6d9ce85e4d3d3a70
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_string_table_reader.cpp
@@ -0,0 +1,88 @@
+#include "resource_string_table_reader.h"
+#include "pe_resource_viewer.h"
+
+namespace pe_bliss
+{
+resource_string_table_reader::resource_string_table_reader(const pe_resource_viewer& res)
+	:res_(res)
+{}
+
+//Returns string table data by ID and index in language directory (instead of language)
+const resource_string_list resource_string_table_reader::get_string_table_by_id(uint32_t id, uint32_t index) const
+{
+	return parse_string_list(id, res_.get_resource_data_by_id(pe_resource_viewer::resource_string, id, index).get_data());
+}
+
+//Returns string table data by ID and language
+const resource_string_list resource_string_table_reader::get_string_table_by_id_lang(uint32_t language, uint32_t id) const
+{
+	return parse_string_list(id, res_.get_resource_data_by_id(language, pe_resource_viewer::resource_string, id).get_data());
+}
+
+//Helper function of parsing string list table
+const resource_string_list resource_string_table_reader::parse_string_list(uint32_t id, const std::string& resource_data)
+{
+	resource_string_list ret;
+
+	//16 is maximum count of strings in a string table
+	static const unsigned long max_string_list_entries = 16;
+	unsigned long passed_bytes = 0;
+	for(unsigned long i = 0; i != max_string_list_entries; ++i)
+	{
+		//Check resource data length
+		if(resource_data.length() < sizeof(uint16_t) + passed_bytes)
+			throw pe_exception("Incorrect resource string table", pe_exception::resource_incorrect_string_table);
+
+		//Get string length - the first WORD
+		uint16_t string_length = *reinterpret_cast<const uint16_t*>(resource_data.data() + passed_bytes);
+		passed_bytes += sizeof(uint16_t); //WORD containing string length
+
+		//Check resource data length again
+		if(resource_data.length() < string_length + passed_bytes)
+			throw pe_exception("Incorrect resource string table", pe_exception::resource_incorrect_string_table);
+
+		if(string_length)
+		{
+			//Create and save string (UNICODE)
+#ifdef PE_BLISS_WINDOWS
+			ret.insert(
+				std::make_pair(static_cast<uint16_t>(((id - 1) << 4) + i), //ID of string is calculated such way
+				std::wstring(reinterpret_cast<const wchar_t*>(resource_data.data() + passed_bytes), string_length)));
+#else
+			ret.insert(
+				std::make_pair(static_cast<uint16_t>(((id - 1) << 4) + i), //ID of string is calculated such way
+				pe_utils::from_ucs2(u16string(reinterpret_cast<const unicode16_t*>(resource_data.data() + passed_bytes), string_length))));
+#endif
+		}
+
+		//Go to next string
+		passed_bytes += string_length * 2;
+	}
+
+	return ret;
+}
+
+//Returns string from string table by ID and language
+const std::wstring resource_string_table_reader::get_string_by_id_lang(uint32_t language, uint16_t id) const
+{
+	//List strings by string table id and language
+	const resource_string_list strings(get_string_table_by_id_lang(language, (id >> 4) + 1));
+	resource_string_list::const_iterator it = strings.find(id); //Find string by id
+	if(it == strings.end())
+		throw pe_exception("Resource string not found", pe_exception::resource_string_not_found);
+
+	return (*it).second;
+}
+
+//Returns string from string table by ID and index in language directory (instead of language)
+const std::wstring resource_string_table_reader::get_string_by_id(uint16_t id, uint32_t index) const
+{
+	//List strings by string table id and index
+	const resource_string_list strings(get_string_table_by_id((id >> 4) + 1, index));
+	resource_string_list::const_iterator it = strings.find(id); //Find string by id
+	if(it == strings.end())
+		throw pe_exception("Resource string not found", pe_exception::resource_string_not_found);
+
+	return (*it).second;
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_string_table_reader.h b/irdb-lib/pebliss/trunk/pe_lib/resource_string_table_reader.h
new file mode 100644
index 0000000000000000000000000000000000000000..cd3e754cbfb04db8e1d802edceed8fe599cc5961
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_string_table_reader.h
@@ -0,0 +1,39 @@
+#ifndef pebliss_resource_string_table_reader_h
+#define pebliss_resource_string_table_reader_h
+#pragma once
+#include <string>
+#include <map>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+class pe_resource_viewer;
+
+//ID; string
+typedef std::map<uint16_t, std::wstring> resource_string_list;
+
+class resource_string_table_reader
+{
+public:
+	resource_string_table_reader(const pe_resource_viewer& res);
+
+public:
+	//Returns string table data by ID and language
+	const resource_string_list get_string_table_by_id_lang(uint32_t language, uint32_t id) const;
+	//Returns string table data by ID and index in language directory (instead of language)
+	const resource_string_list get_string_table_by_id(uint32_t id, uint32_t index = 0) const;
+	//Returns string from string table by ID and language
+	const std::wstring get_string_by_id_lang(uint32_t language, uint16_t id) const;
+	//Returns string from string table by ID and index in language directory (instead of language)
+	const std::wstring get_string_by_id(uint16_t id, uint32_t index = 0) const;
+
+private:
+	const pe_resource_viewer& res_;
+
+	//Helper function of parsing string list table
+	//Id of resource is needed to calculate string IDs correctly
+	//resource_data is raw string table resource data
+	static const resource_string_list parse_string_list(uint32_t id, const std::string& resource_data);
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_reader.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_reader.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..4a8a2723e60f0e41722d3a4cf536db8258ad9c3a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_reader.cpp
@@ -0,0 +1,290 @@
+#include "resource_version_info_reader.h"
+#include "utils.h"
+#include "pe_exception.h"
+#include "resource_internal.h"
+#include "pe_resource_viewer.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+//Root version info block key value
+const u16string resource_version_info_reader::version_info_key(U16TEXT("V\0S\0_\0V\0E\0R\0S\0I\0O\0N\0_\0I\0N\0F\0O\0\0"));
+
+resource_version_info_reader::resource_version_info_reader(const pe_resource_viewer& res)
+	:res_(res)
+{}
+
+//Returns aligned version block value position
+uint32_t resource_version_info_reader::get_version_block_value_pos(uint32_t base_pos, const unicode16_t* key)
+{
+	uint32_t string_length = static_cast<uint32_t>(u16string(key).length());
+	uint32_t ret = pe_utils::align_up(static_cast<uint32_t>(sizeof(uint16_t) * 3 /* headers before Key data */
+		+ base_pos
+		+ (string_length + 1 /* nullbyte */) * 2),
+		sizeof(uint32_t));
+
+	//Check possible overflows
+	if(ret < base_pos || ret < sizeof(uint16_t) * 3 || ret < (string_length + 1) * 2)
+		throw_incorrect_version_info();
+
+	return ret;
+}
+
+//Returns aligned version block first child position
+uint32_t resource_version_info_reader::get_version_block_first_child_pos(uint32_t base_pos, uint32_t value_length, const unicode16_t* key)
+{
+	uint32_t string_length = static_cast<uint32_t>(u16string(key).length());
+	uint32_t ret =  pe_utils::align_up(static_cast<uint32_t>(sizeof(uint16_t) * 3 /* headers before Key data */
+		+ base_pos
+		+ (string_length + 1 /* nullbyte */) * 2),
+		sizeof(uint32_t))
+		+ pe_utils::align_up(value_length, sizeof(uint32_t));
+
+	//Check possible overflows
+	if(ret < base_pos || ret < value_length || ret < sizeof(uint16_t) * 3 || ret < (string_length + 1) * 2)
+		throw_incorrect_version_info();
+
+	return ret;
+}
+
+//Throws an exception (id = resource_incorrect_version_info)
+void resource_version_info_reader::throw_incorrect_version_info()
+{
+	throw pe_exception("Incorrect resource version info", pe_exception::resource_incorrect_version_info);
+}
+
+//Returns full version information:
+//file_version_info: versions and file info
+//lang_string_values_map: map of version info strings with encodings
+//translation_values_map: map of translations
+const file_version_info resource_version_info_reader::get_version_info(lang_string_values_map& string_values, translation_values_map& translations, const std::string& resource_data) const
+{
+	//Fixed file version info
+	file_version_info ret;
+
+	//Check resource data length
+	if(resource_data.length() < sizeof(version_info_block))
+		throw_incorrect_version_info();
+
+	//Root version info block
+	const version_info_block* root_block = reinterpret_cast<const version_info_block*>(resource_data.data());
+
+	//Check root block key for null-termination and its name
+	if(!pe_utils::is_null_terminated(root_block->Key, resource_data.length() - sizeof(uint16_t) * 3 /* headers before Key data */)
+		|| version_info_key != reinterpret_cast<const unicode16_t*>(root_block->Key))
+		throw_incorrect_version_info();
+
+	//If file has fixed version info
+	if(root_block->ValueLength)
+	{
+		//Get root block value position
+		uint32_t value_pos = get_version_block_value_pos(0, reinterpret_cast<const unicode16_t*>(root_block->Key));
+		//Check value length
+		if(resource_data.length() < value_pos + sizeof(vs_fixedfileinfo))
+			throw_incorrect_version_info();
+
+		//Get VS_FIXEDFILEINFO structure pointer
+		const vs_fixedfileinfo* file_info = reinterpret_cast<const vs_fixedfileinfo*>(resource_data.data() + value_pos);
+		//Check its signature and some other fields
+		if(file_info->dwSignature != vs_ffi_signature || file_info->dwStrucVersion != vs_ffi_strucversion) //Don't check if file_info->dwFileFlagsMask == VS_FFI_FILEFLAGSMASK
+			throw_incorrect_version_info();
+
+		//Save fixed version info
+		ret = file_version_info(*file_info);
+	}
+
+	//Iterate over child elements of VS_VERSIONINFO (StringFileInfo or VarFileInfo)
+	for(uint32_t child_pos = get_version_block_first_child_pos(0, root_block->ValueLength, reinterpret_cast<const unicode16_t*>(root_block->Key));
+		child_pos < root_block->Length;)
+	{
+		//Check block position
+		if(!pe_utils::is_sum_safe(child_pos, sizeof(version_info_block))
+			|| resource_data.length() < child_pos + sizeof(version_info_block))
+			throw_incorrect_version_info();
+
+		//Get VERSION_INFO_BLOCK structure pointer
+		const version_info_block* block = reinterpret_cast<const version_info_block*>(resource_data.data() + child_pos);
+
+		//Check its length
+		if(block->Length == 0)
+			throw_incorrect_version_info();
+
+		//Check block key for null-termination
+		if(!pe_utils::is_null_terminated(block->Key, resource_data.length() - child_pos - sizeof(uint16_t) * 3 /* headers before Key data */))
+			throw_incorrect_version_info();
+
+		u16string info_type(reinterpret_cast<const unicode16_t*>(block->Key));
+		//If we encountered StringFileInfo...
+		if(info_type == StringFileInfo)
+		{
+			//Enumerate all string tables
+			for(uint32_t string_table_pos = get_version_block_first_child_pos(child_pos, block->ValueLength, reinterpret_cast<const unicode16_t*>(block->Key));
+				string_table_pos - child_pos < block->Length;)
+			{
+				//Check string table block position
+				if(resource_data.length() < string_table_pos + sizeof(version_info_block))
+					throw_incorrect_version_info();
+
+				//Get VERSION_INFO_BLOCK structure pointer for string table
+				const version_info_block* string_table = reinterpret_cast<const version_info_block*>(resource_data.data() + string_table_pos);
+
+				//Check its length
+				if(string_table->Length == 0)
+					throw_incorrect_version_info();
+
+				//Check string table key for null-termination
+				if(!pe_utils::is_null_terminated(string_table->Key, resource_data.length() - string_table_pos - sizeof(uint16_t) * 3 /* headers before Key data */))	
+					throw_incorrect_version_info();
+
+				string_values_map new_values;
+
+				//Enumerate all strings in the string table
+				for(uint32_t string_pos = get_version_block_first_child_pos(string_table_pos, string_table->ValueLength, reinterpret_cast<const unicode16_t*>(string_table->Key));
+					string_pos - string_table_pos < string_table->Length;)
+				{
+					//Check string block position
+					if(resource_data.length() < string_pos + sizeof(version_info_block))
+						throw_incorrect_version_info();
+
+					//Get VERSION_INFO_BLOCK structure pointer for string block
+					const version_info_block* string_block = reinterpret_cast<const version_info_block*>(resource_data.data() + string_pos);
+
+					//Check its length
+					if(string_block->Length == 0)
+						throw_incorrect_version_info();
+
+					//Check string block key for null-termination
+					if(!pe_utils::is_null_terminated(string_block->Key, resource_data.length() - string_pos - sizeof(uint16_t) * 3 /* headers before Key data */))
+						throw_incorrect_version_info();
+
+					u16string data;
+					//If string block has value
+					if(string_block->ValueLength != 0)
+					{
+						//Get value position
+						uint32_t value_pos = get_version_block_value_pos(string_pos, reinterpret_cast<const unicode16_t*>(string_block->Key));
+						//Check it
+						if(resource_data.length() < value_pos + string_block->ValueLength)
+							throw pe_exception("Incorrect resource version info", pe_exception::resource_incorrect_version_info);
+
+						//Get UNICODE string value
+						data = u16string(reinterpret_cast<const unicode16_t*>(resource_data.data() + value_pos), string_block->ValueLength);
+						pe_utils::strip_nullbytes(data);
+					}
+
+					//Save name-value pair
+#ifdef PE_BLISS_WINDOWS
+					new_values.insert(std::make_pair(reinterpret_cast<const unicode16_t*>(string_block->Key), data));
+#else
+					new_values.insert(std::make_pair(pe_utils::from_ucs2(reinterpret_cast<const unicode16_t*>(string_block->Key)),
+						pe_utils::from_ucs2(data)));
+#endif
+
+					//Navigate to next string block
+					string_pos += pe_utils::align_up(string_block->Length, sizeof(uint32_t));
+				}
+
+#ifdef PE_BLISS_WINDOWS
+				string_values.insert(std::make_pair(reinterpret_cast<const unicode16_t*>(string_table->Key), new_values));
+#else
+				string_values.insert(std::make_pair(pe_utils::from_ucs2(reinterpret_cast<const unicode16_t*>(string_table->Key)), new_values));
+#endif
+
+				//Navigate to next string table block
+				string_table_pos += pe_utils::align_up(string_table->Length, sizeof(uint32_t));
+			}
+		}
+		else if(info_type == VarFileInfo) //If we encountered VarFileInfo
+		{
+			for(uint32_t var_table_pos = get_version_block_first_child_pos(child_pos, block->ValueLength, reinterpret_cast<const unicode16_t*>(block->Key));
+				var_table_pos - child_pos < block->Length;)
+			{
+				//Check var block position
+				if(resource_data.length() < var_table_pos + sizeof(version_info_block))
+					throw_incorrect_version_info();
+
+				//Get VERSION_INFO_BLOCK structure pointer for var block
+				const version_info_block* var_table = reinterpret_cast<const version_info_block*>(resource_data.data() + var_table_pos);
+
+				//Check its length
+				if(var_table->Length == 0)
+					throw_incorrect_version_info();
+
+				//Check its key for null-termination
+				if(!pe_utils::is_null_terminated(var_table->Key, resource_data.length() - var_table_pos - sizeof(uint16_t) * 3 /* headers before Key data */))
+					throw_incorrect_version_info();
+
+				//If block is "Translation" (actually, there's no other types possible in VarFileInfo) and it has value
+				if(u16string(reinterpret_cast<const unicode16_t*>(var_table->Key)) == Translation && var_table->ValueLength)
+				{
+					//Get its value position
+					uint32_t value_pos = get_version_block_value_pos(var_table_pos, reinterpret_cast<const unicode16_t*>(var_table->Key));
+					//Cherck value length
+					if(resource_data.length() < value_pos + var_table->ValueLength)
+						throw_incorrect_version_info();
+
+					//Get list of translations: pairs of LANGUAGE_ID - CODEPAGE_ID
+					for(unsigned long i = 0; i < var_table->ValueLength; i += sizeof(uint16_t) * 2)
+					{
+						//Pair of WORDs
+						uint16_t lang_id = *reinterpret_cast<const uint16_t*>(resource_data.data() + value_pos + i);
+						uint16_t codepage_id = *reinterpret_cast<const uint16_t*>(resource_data.data() + value_pos + sizeof(uint16_t) + i);
+						//Save translation
+						translations.insert(std::make_pair(lang_id, codepage_id));
+					}
+				}
+
+				//Navigate to next var block
+				var_table_pos += pe_utils::align_up(var_table->Length, sizeof(uint32_t));
+			}
+		}
+		else
+		{
+			throw_incorrect_version_info();
+		}
+
+		//Navigate to next element in root block
+		child_pos += pe_utils::align_up(block->Length, sizeof(uint32_t));
+	}
+
+	return ret;
+}
+
+//Returns full version information:
+//file_version info: versions and file info
+//lang_string_values_map: map of version info strings with encodings
+//translation_values_map: map of translations
+const file_version_info resource_version_info_reader::get_version_info_by_lang(lang_string_values_map& string_values, translation_values_map& translations, uint32_t language) const
+{
+	const std::string& resource_data = res_.get_root_directory() //Type directory
+		.entry_by_id(pe_resource_viewer::resource_version)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(1)
+		.get_resource_directory() //Language directory
+		.entry_by_id(language)
+		.get_data_entry() //Data directory
+		.get_data();
+
+	return get_version_info(string_values, translations, resource_data);
+}
+
+//Returns full version information:
+//file_version_info: versions and file info
+//lang_string_values_map: map of version info strings with encodings
+//translation_values_map: map of translations
+const file_version_info resource_version_info_reader::get_version_info(lang_string_values_map& string_values, translation_values_map& translations, uint32_t index) const
+{
+	const resource_directory::entry_list& entries = res_.get_root_directory() //Type directory
+		.entry_by_id(pe_resource_viewer::resource_version)
+		.get_resource_directory() //Name/ID directory
+		.entry_by_id(1)
+		.get_resource_directory() //Language directory
+		.get_entry_list();
+
+	if(entries.size() <= index)
+		throw pe_exception("Resource data entry not found", pe_exception::resource_data_entry_not_found);
+
+	return get_version_info(string_values, translations, entries.at(index).get_data_entry().get_data()); //Data directory
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_reader.h b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_reader.h
new file mode 100644
index 0000000000000000000000000000000000000000..e85c297b251bee472ca4855b48325ac98cf978f0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_reader.h
@@ -0,0 +1,49 @@
+#ifndef pebliss_resource_version_info_reader_h
+#define pebliss_resource_version_info_reader_h
+#pragma once
+#include <map>
+#include "file_version_info.h"
+#include "pe_structures.h"
+#include "version_info_types.h"
+
+namespace pe_bliss
+{
+class pe_resource_viewer;
+
+class resource_version_info_reader
+{
+public: //VERSION INFO
+	resource_version_info_reader(const pe_resource_viewer& res);
+
+	//Returns full version information:
+	//file_version_info: versions and file info
+	//lang_lang_string_values_map: map of version info strings with encodings with encodings
+	//translation_values_map: map of translations
+	const file_version_info get_version_info(lang_string_values_map& string_values, translation_values_map& translations, uint32_t index = 0) const;
+	const file_version_info get_version_info_by_lang(lang_string_values_map& string_values, translation_values_map& translations, uint32_t language) const;
+
+public:
+	//L"VS_VERSION_INFO" key of root version info block
+	static const u16string version_info_key;
+
+private:
+	const pe_resource_viewer& res_;
+	
+	//VERSION INFO helpers
+	//Returns aligned version block value position
+	static uint32_t get_version_block_value_pos(uint32_t base_pos, const unicode16_t* key);
+
+	//Returns aligned version block first child position
+	static uint32_t get_version_block_first_child_pos(uint32_t base_pos, uint32_t value_length, const unicode16_t* key);
+
+	//Returns full version information:
+	//file_version_info: versions and file info
+	//lang_string_values_map: map of version info strings with encodings
+	//translation_values_map: map of translations
+	const file_version_info get_version_info(lang_string_values_map& string_values, translation_values_map& translations, const std::string& resource_data) const;
+
+	//Throws an exception (id = resource_incorrect_version_info)
+	static void throw_incorrect_version_info();
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_writer.cpp b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_writer.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..34f21c4a378a56fd13b2138e1bb4f80568de2d82
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_writer.cpp
@@ -0,0 +1,262 @@
+#include <string.h>
+#include "resource_version_info_writer.h"
+#include "pe_structures.h"
+#include "resource_internal.h"
+#include "utils.h"
+#include "pe_resource_manager.h"
+#include "resource_version_info_reader.h"
+
+namespace pe_bliss
+{
+using namespace pe_win;
+
+resource_version_info_writer::resource_version_info_writer(pe_resource_manager& res)
+	:res_(res)
+{}
+
+//Sets/replaces full version information:
+//file_version_info: versions and file info
+//lang_string_values_map: map of version info strings with encodings
+//translation_values_map: map of translations
+void resource_version_info_writer::set_version_info(const file_version_info& file_info,
+	const lang_string_values_map& string_values,
+	const translation_values_map& translations,
+	uint32_t language,
+	uint32_t codepage,
+	uint32_t timestamp)
+{
+	std::string version_data;
+
+	//Calculate total size of version resource data
+	uint32_t total_version_info_length =
+		static_cast<uint32_t>(sizeof(version_info_block) - sizeof(uint16_t) + sizeof(uint16_t) /* pading */
+		+ (resource_version_info_reader::version_info_key.length() + 1) * 2
+		+ sizeof(vs_fixedfileinfo));
+
+	//If we have any strings values
+	if(!string_values.empty())
+	{
+		total_version_info_length += sizeof(version_info_block) - sizeof(uint16_t); //StringFileInfo block
+		total_version_info_length += SizeofStringFileInfo; //Name of block (key)
+
+		//Add required size for version strings
+		for(lang_string_values_map::const_iterator table_it = string_values.begin(); table_it != string_values.end(); ++table_it)
+		{
+			total_version_info_length += pe_utils::align_up(static_cast<uint32_t>(sizeof(uint16_t) * 3 + ((*table_it).first.length() + 1) * 2), sizeof(uint32_t)); //Name of child block and block size (key of string table block)
+
+			const string_values_map& values = (*table_it).second;
+			for(string_values_map::const_iterator it = values.begin(); it != values.end(); ++it)
+			{
+				total_version_info_length += pe_utils::align_up(static_cast<uint32_t>(sizeof(uint16_t) * 3 + ((*it).first.length() + 1) * 2), sizeof(uint32_t));
+				total_version_info_length += pe_utils::align_up(static_cast<uint32_t>(((*it).second.length() + 1) * 2), sizeof(uint32_t));
+			}
+		}
+	}
+
+	//If we have translations
+	if(!translations.empty())
+	{
+		total_version_info_length += (sizeof(version_info_block) - sizeof(uint16_t)) * 2; //VarFileInfo and Translation blocks
+		total_version_info_length += SizeofVarFileInfoAligned; //DWORD-aligned VarFileInfo block name
+		total_version_info_length += SizeofTranslationAligned; //DWORD-aligned Translation block name
+		total_version_info_length += static_cast<uint32_t>(translations.size() * sizeof(uint16_t) * 2);
+	}
+
+	//Resize version data buffer
+	version_data.resize(total_version_info_length);
+
+	//Create root version block
+	version_info_block root_block = {0};
+	root_block.ValueLength = sizeof(vs_fixedfileinfo);
+	root_block.Length = static_cast<uint16_t>(total_version_info_length);
+
+	//Fill fixed file info
+	vs_fixedfileinfo fixed_info = {0};
+	fixed_info.dwFileDateLS = file_info.get_file_date_ls();
+	fixed_info.dwFileDateMS = file_info.get_file_date_ms();
+	fixed_info.dwFileFlags = file_info.get_file_flags();
+	fixed_info.dwFileFlagsMask = vs_ffi_fileflagsmask;
+	fixed_info.dwFileOS = file_info.get_file_os_raw();
+	fixed_info.dwFileSubtype = file_info.get_file_subtype();
+	fixed_info.dwFileType = file_info.get_file_type_raw();
+	fixed_info.dwFileVersionLS = file_info.get_file_version_ls();
+	fixed_info.dwFileVersionMS = file_info.get_file_version_ms();
+	fixed_info.dwSignature = vs_ffi_signature;
+	fixed_info.dwStrucVersion = vs_ffi_strucversion;
+	fixed_info.dwProductVersionLS = file_info.get_product_version_ls();
+	fixed_info.dwProductVersionMS = file_info.get_product_version_ms();
+
+	//Write root block and fixed file info to buffer
+	uint32_t data_ptr = 0;
+	memcpy(&version_data[data_ptr], &root_block, sizeof(version_info_block) - sizeof(uint16_t));
+	data_ptr += sizeof(version_info_block) - sizeof(uint16_t);
+	memcpy(&version_data[data_ptr], resource_version_info_reader::version_info_key.c_str(), (resource_version_info_reader::version_info_key.length() + 1) * sizeof(uint16_t));
+	data_ptr += static_cast<uint32_t>((resource_version_info_reader::version_info_key.length() + 1) * sizeof(uint16_t));
+	memset(&version_data[data_ptr], 0, sizeof(uint16_t));
+	data_ptr += sizeof(uint16_t);
+	memcpy(&version_data[data_ptr], &fixed_info, sizeof(fixed_info));
+	data_ptr += sizeof(fixed_info);
+
+	//Write string values, if any
+	if(!string_values.empty())
+	{
+		//Create string file info root block
+		version_info_block string_file_info_block = {0};
+		string_file_info_block.Type = 1; //Block type is string
+		memcpy(&version_data[data_ptr], &string_file_info_block, sizeof(version_info_block) - sizeof(uint16_t));
+		//We will calculate its length later
+		version_info_block* string_file_info_block_ptr = reinterpret_cast<version_info_block*>(&version_data[data_ptr]);
+		data_ptr += sizeof(version_info_block) - sizeof(uint16_t);
+
+		uint32_t old_ptr1 = data_ptr; //Used to calculate string file info block length later
+		memcpy(&version_data[data_ptr], StringFileInfo, SizeofStringFileInfo); //Write block name
+		data_ptr += SizeofStringFileInfo;
+
+		//Create string table root block (child of string file info)
+		version_info_block string_table_block = {0};
+		string_table_block.Type = 1; //Block type is string
+
+		for(lang_string_values_map::const_iterator table_it = string_values.begin(); table_it != string_values.end(); ++table_it)
+		{
+			const string_values_map& values = (*table_it).second;
+
+			memcpy(&version_data[data_ptr], &string_table_block, sizeof(version_info_block) - sizeof(uint16_t));
+			//We will calculate its length later
+			version_info_block* string_table_block_ptr = reinterpret_cast<version_info_block*>(&version_data[data_ptr]);
+			data_ptr += sizeof(version_info_block) - sizeof(uint16_t);
+
+			uint32_t old_ptr2 = data_ptr; //Used to calculate string table block length later
+			uint32_t lang_key_length = static_cast<uint32_t>(((*table_it).first.length() + 1) * sizeof(uint16_t));
+
+#ifdef PE_BLISS_WINDOWS
+			memcpy(&version_data[data_ptr], (*table_it).first.c_str(), lang_key_length); //Write block key
+#else
+			{
+				u16string str(pe_utils::to_ucs2((*table_it).first));
+				memcpy(&version_data[data_ptr], str.c_str(), lang_key_length); //Write block key
+			}
+#endif
+
+			data_ptr += lang_key_length;
+			//Align key if necessary
+			if((sizeof(uint16_t) * 3 + lang_key_length) % sizeof(uint32_t))
+			{
+				memset(&version_data[data_ptr], 0, sizeof(uint16_t));
+				data_ptr += sizeof(uint16_t);
+			}
+
+			//Create string block (child of string table block)
+			version_info_block string_block = {0};
+			string_block.Type = 1; //Block type is string
+			for(string_values_map::const_iterator it = values.begin(); it != values.end(); ++it)
+			{
+				//Calculate value length and key length of string block
+				string_block.ValueLength = static_cast<uint16_t>((*it).second.length() + 1);
+				uint32_t key_length = static_cast<uint32_t>(((*it).first.length() + 1) * sizeof(uint16_t));
+				//Calculate length of block
+				string_block.Length = static_cast<uint16_t>(pe_utils::align_up(sizeof(uint16_t) * 3 + key_length, sizeof(uint32_t)) + string_block.ValueLength * sizeof(uint16_t));
+
+				//Write string block
+				memcpy(&version_data[data_ptr], &string_block, sizeof(version_info_block) - sizeof(uint16_t));
+				data_ptr += sizeof(version_info_block) - sizeof(uint16_t);
+
+#ifdef PE_BLISS_WINDOWS
+				memcpy(&version_data[data_ptr], (*it).first.c_str(), key_length); //Write block key
+#else
+				{
+					u16string str(pe_utils::to_ucs2((*it).first));
+					memcpy(&version_data[data_ptr], str.c_str(), key_length); //Write block key
+				}
+#endif
+
+				data_ptr += key_length;
+				//Align key if necessary
+				if((sizeof(uint16_t) * 3 + key_length) % sizeof(uint32_t))
+				{
+					memset(&version_data[data_ptr], 0, sizeof(uint16_t));
+					data_ptr += sizeof(uint16_t);
+				}
+
+				//Write block data (value)
+#ifdef PE_BLISS_WINDOWS
+				memcpy(&version_data[data_ptr], (*it).second.c_str(), string_block.ValueLength * sizeof(uint16_t));
+#else
+				{
+					u16string str(pe_utils::to_ucs2((*it).second));
+					memcpy(&version_data[data_ptr], str.c_str(), string_block.ValueLength * sizeof(uint16_t));
+				}
+#endif
+
+				data_ptr += string_block.ValueLength * 2;
+				//Align data if necessary
+				if((string_block.ValueLength * 2) % sizeof(uint32_t))
+				{
+					memset(&version_data[data_ptr], 0, sizeof(uint16_t));
+					data_ptr += sizeof(uint16_t);
+				}
+			}
+
+			//Calculate string table and string file info blocks lengths
+			string_table_block_ptr->Length = static_cast<uint16_t>(data_ptr - old_ptr2 + sizeof(uint16_t) * 3);
+		}
+
+		string_file_info_block_ptr->Length = static_cast<uint16_t>(data_ptr - old_ptr1 + sizeof(uint16_t) * 3);
+	}
+
+	//If we have transactions
+	if(!translations.empty())
+	{
+		//Create root var file info block
+		version_info_block var_file_info_block = {0};
+		var_file_info_block.Type = 1; //Type of block is string
+		//Write block header
+		memcpy(&version_data[data_ptr], &var_file_info_block, sizeof(version_info_block) - sizeof(uint16_t));
+		//We will calculate its length later
+		version_info_block* var_file_info_block_ptr = reinterpret_cast<version_info_block*>(&version_data[data_ptr]);
+		data_ptr += sizeof(version_info_block) - sizeof(uint16_t);
+
+		uint32_t old_ptr1 = data_ptr; //Used to calculate var file info block length later
+		memcpy(&version_data[data_ptr], VarFileInfoAligned, SizeofVarFileInfoAligned); //Write block key (aligned)
+		data_ptr += SizeofVarFileInfoAligned;
+
+		//Create root translation block (child of var file info block)
+		version_info_block translation_block = {0};
+		//Write block header
+		memcpy(&version_data[data_ptr], &translation_block, sizeof(version_info_block) - sizeof(uint16_t));
+		//We will calculate its length later
+		version_info_block* translation_block_ptr = reinterpret_cast<version_info_block*>(&version_data[data_ptr]);
+		data_ptr += sizeof(version_info_block) - sizeof(uint16_t);
+
+		uint32_t old_ptr2 = data_ptr; //Used to calculate var file info block length later
+		memcpy(&version_data[data_ptr], TranslationAligned, SizeofTranslationAligned); //Write block key (aligned)
+		data_ptr += SizeofTranslationAligned;
+
+		//Calculate translation block value length
+		translation_block_ptr->ValueLength = static_cast<uint16_t>(sizeof(uint16_t) * 2 * translations.size());
+
+		//Write translation values to block
+		for(translation_values_map::const_iterator it = translations.begin(); it != translations.end(); ++it)
+		{
+			uint16_t lang_id = (*it).first; //Language ID
+			uint16_t codepage_id = (*it).second; //Codepage ID
+			memcpy(&version_data[data_ptr], &lang_id, sizeof(lang_id));
+			data_ptr += sizeof(lang_id);
+			memcpy(&version_data[data_ptr], &codepage_id, sizeof(codepage_id));
+			data_ptr += sizeof(codepage_id);
+		}
+
+		//Calculate Translation and VarFileInfo blocks lengths
+		translation_block_ptr->Length = static_cast<uint16_t>(data_ptr - old_ptr2 + sizeof(uint16_t) * 3);
+		var_file_info_block_ptr->Length = static_cast<uint16_t>(data_ptr - old_ptr1 + sizeof(uint16_t) * 3);
+	}
+
+	//Add/replace version info resource
+	res_.add_resource(version_data, pe_resource_viewer::resource_version, 1, language, codepage, timestamp);
+}
+
+//Removes version info by language (ID = 1)
+bool resource_version_info_writer::remove_version_info(uint32_t language)
+{
+	return res_.remove_resource(pe_resource_viewer::resource_version, 1, language);
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_writer.h b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_writer.h
new file mode 100644
index 0000000000000000000000000000000000000000..8f65c5dd2bc7d0b05e2edc8bf33f0937aca04ed4
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/resource_version_info_writer.h
@@ -0,0 +1,34 @@
+#ifndef pebliss_resource_version_info_writer_h
+#define pebliss_resource_version_info_writer_h
+#pragma once
+#include "version_info_types.h"
+#include "file_version_info.h"
+
+namespace pe_bliss
+{
+class pe_resource_manager;
+
+class resource_version_info_writer
+{
+public:
+	resource_version_info_writer(pe_resource_manager& res);
+	
+	//Sets/replaces full version information:
+	//file_version_info: versions and file info
+	//lang_string_values_map: map of version info strings with encodings
+	//translation_values_map: map of translations
+	void set_version_info(const file_version_info& file_info,
+		const lang_string_values_map& string_values,
+		const translation_values_map& translations,
+		uint32_t language,
+		uint32_t codepage = 0,
+		uint32_t timestamp = 0);
+	
+	//Removes version info by language (ID = 1)
+	bool remove_version_info(uint32_t language);
+
+private:
+	pe_resource_manager& res_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/stdint_defs.h b/irdb-lib/pebliss/trunk/pe_lib/stdint_defs.h
new file mode 100644
index 0000000000000000000000000000000000000000..51b25f743a63e710af959fed9bb8f2b9e59eba01
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/stdint_defs.h
@@ -0,0 +1,27 @@
+#ifndef pebliss_stdint_defs_h
+#define pebliss_stdint_defs_h
+#pragma once
+#ifdef _MSC_VER
+#if _MSC_VER < 1600
+namespace pe_bliss
+{
+	//stdint.h definitions for MSVC 2008 and earlier, as
+	//it doesn't have them
+	typedef signed char int8_t;
+	typedef short int16_t;
+	typedef int int32_t;
+
+	typedef unsigned char uint8_t;
+	typedef unsigned short uint16_t;
+	typedef unsigned int uint32_t;
+
+	typedef long long int64_t;
+	typedef unsigned long long uint64_t;
+}
+#else
+#include <stdint.h>
+#endif
+#else
+#include <stdint.h>
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/utils.cpp b/irdb-lib/pebliss/trunk/pe_lib/utils.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..917184d8170a8e61466fc44f20f5768621dffa6f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/utils.cpp
@@ -0,0 +1,87 @@
+#include <string.h>
+#include "utils.h"
+#include "pe_exception.h"
+
+#ifndef PE_BLISS_WINDOWS
+#include <iconv.h>
+#endif
+
+namespace pe_bliss
+{
+const double pe_utils::log_2 = 1.44269504088896340736; //instead of using M_LOG2E
+
+//Returns stream size
+std::streamoff pe_utils::get_file_size(std::istream& file)
+{
+	//Get old istream offset
+	std::streamoff old_offset = file.tellg();
+	file.seekg(0, std::ios::end);
+	std::streamoff filesize = file.tellg();
+	//Set old istream offset
+	file.seekg(old_offset);
+	return filesize;
+}
+
+#ifndef PE_BLISS_WINDOWS
+const u16string pe_utils::to_ucs2(const std::wstring& str)
+{
+	u16string ret;
+	if(str.empty())
+		return ret;
+
+	ret.resize(str.length());
+
+	iconv_t conv = iconv_open("UCS-2", "WCHAR_T");
+	if(conv == reinterpret_cast<iconv_t>(-1))
+		throw pe_exception("Error opening iconv", pe_exception::encoding_convertion_error);
+
+	size_t inbytesleft = str.length() * sizeof(wchar_t);
+	size_t outbytesleft = ret.length() * sizeof(unicode16_t);
+	const wchar_t* in_pos = str.c_str();
+	unicode16_t* out_pos = &ret[0];
+
+	size_t result = iconv(conv, const_cast<char**>(reinterpret_cast<const char**>(&in_pos)), &inbytesleft, reinterpret_cast<char**>(&out_pos), &outbytesleft);
+
+	iconv_close(conv);
+	
+	if(result == static_cast<size_t>(-1))
+		throw pe_exception("Iconv error", pe_exception::encoding_convertion_error);
+
+	return ret;
+}
+
+const std::wstring pe_utils::from_ucs2(const u16string& str)
+{
+	std::wstring ret;
+	if(str.empty())
+		return ret;
+
+	ret.resize(str.length());
+
+	iconv_t conv = iconv_open("WCHAR_T", "UCS-2");
+	if(conv == reinterpret_cast<iconv_t>(-1))
+		throw pe_exception("Error opening iconv", pe_exception::encoding_convertion_error);
+
+	size_t inbytesleft = str.length() * sizeof(unicode16_t);
+	size_t outbytesleft = ret.length() * sizeof(wchar_t);
+	const unicode16_t* in_pos = str.c_str();
+	wchar_t* out_pos = &ret[0];
+
+	size_t result = iconv(conv, const_cast<char**>(reinterpret_cast<const char**>(&in_pos)), &inbytesleft, reinterpret_cast<char**>(&out_pos), &outbytesleft);
+	iconv_close(conv);
+
+	if(result == static_cast<size_t>(-1))
+		throw pe_exception("Iconv error", pe_exception::encoding_convertion_error);
+
+	return ret;
+}
+#endif
+
+bool operator==(const pe_win::guid& guid1, const pe_win::guid& guid2)
+{
+	return guid1.Data1 == guid2.Data1
+		&& guid1.Data2 == guid2.Data2
+		&& guid1.Data3 == guid2.Data3
+		&& !memcmp(guid1.Data4, guid2.Data4, sizeof(guid1.Data4));
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/utils.h b/irdb-lib/pebliss/trunk/pe_lib/utils.h
new file mode 100644
index 0000000000000000000000000000000000000000..7249b83cec76a05cb19ceb7ba69f69738e70a9b3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/utils.h
@@ -0,0 +1,88 @@
+#ifndef pebliss_utils_h
+#define pebliss_utils_h
+#pragma once
+
+#include <istream>
+#include <string>
+#include "stdint_defs.h"
+#include "pe_structures.h"
+
+namespace pe_bliss
+{
+class pe_utils
+{
+public:
+	//Returns true if string "data" with maximum length "raw_length" is null-terminated
+	template<typename T>
+	static bool is_null_terminated(const T* data, size_t raw_length)
+	{
+		raw_length /= sizeof(T);
+		for(size_t l = 0; l < raw_length; l++)
+		{
+			if(data[l] == static_cast<T>(L'\0'))
+				return true;
+		}
+
+		return false;
+	}
+
+	//Helper template function to strip nullbytes in the end of string
+	template<typename T>
+	static void strip_nullbytes(std::basic_string<T>& str)
+	{
+		while(!*(str.end() - 1) && !str.empty())
+			str.erase(str.length() - 1);
+	}
+
+	//Helper function to determine if number is power of 2
+	template<typename T>
+	static inline bool is_power_of_2(T x)
+	{
+		return !(x & (x - 1));
+	}
+
+	//Helper function to align number down
+	template<typename T>
+	static inline T align_down(T x, uint32_t align)
+	{
+		return x & ~(static_cast<T>(align) - 1);
+	}
+
+	//Helper function to align number up
+	template<typename T>
+	static inline T align_up(T x, uint32_t align)
+	{
+		return (x & static_cast<T>(align - 1)) ? align_down(x, align) + static_cast<T>(align) : x;
+	}
+
+	//Returns true if sum of two unsigned integers is safe (no overflow occurs)
+	static inline bool is_sum_safe(uint32_t a, uint32_t b)
+	{
+		return a <= static_cast<uint32_t>(-1) - b;
+	}
+
+	//Two gigabytes value in bytes
+	static const uint32_t two_gb = 0x80000000;
+	static const uint32_t max_dword = 0xFFFFFFFF;
+	static const uint32_t max_word = 0x0000FFFF;
+	static const double log_2; //instead of using M_LOG2E
+
+	//Returns stream size
+	static std::streamoff get_file_size(std::istream& file);
+	
+#ifndef PE_BLISS_WINDOWS
+public:
+	static const u16string to_ucs2(const std::wstring& str);
+	static const std::wstring from_ucs2(const u16string& str);
+#endif
+
+private:
+	pe_utils();
+	pe_utils(pe_utils&);
+	pe_utils& operator=(const pe_utils&);
+};
+
+//Windows GUID comparison
+bool operator==(const pe_win::guid& guid1, const pe_win::guid& guid2);
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/version_info_editor.cpp b/irdb-lib/pebliss/trunk/pe_lib/version_info_editor.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..9e5c9b7a1c1be96122d62ad9304774ad175978f3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/version_info_editor.cpp
@@ -0,0 +1,163 @@
+#include <sstream>
+#include <iomanip>
+#include "version_info_types.h"
+#include "version_info_editor.h"
+#include "version_info_viewer.h"
+
+namespace pe_bliss
+{
+//Default constructor
+//strings - version info strings with charsets
+//translations - version info translations map
+version_info_editor::version_info_editor(lang_string_values_map& strings, translation_values_map& translations)
+	:version_info_viewer(strings, translations),
+	strings_edit_(strings),
+	translations_edit_(translations)
+{}
+
+//Below functions have parameter translation
+//If it's empty, the default language translation will be taken
+//If there's no default language translation, the first one will be taken
+
+//Sets company name
+void version_info_editor::set_company_name(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"CompanyName", value, translation);
+}
+
+//Sets file description
+void version_info_editor::set_file_description(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"FileDescription", value, translation);
+}
+
+//Sets file version
+void version_info_editor::set_file_version(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"FileVersion", value, translation);
+}
+
+//Sets internal file name
+void version_info_editor::set_internal_name(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"InternalName", value, translation);
+}
+
+//Sets legal copyright
+void version_info_editor::set_legal_copyright(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"LegalCopyright", value, translation);
+}
+
+//Sets original file name
+void version_info_editor::set_original_filename(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"OriginalFilename", value, translation);
+}
+
+//Sets product name
+void version_info_editor::set_product_name(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"ProductName", value, translation);
+}
+
+//Sets product version
+void version_info_editor::set_product_version(const std::wstring& value, const std::wstring& translation)
+{
+	set_property(L"ProductVersion", value, translation);
+}
+
+//Sets version info property value
+//property_name - property name
+//value - property value
+//If translation does not exist, it will be added
+//If property does not exist, it will be added
+void version_info_editor::set_property(const std::wstring& property_name, const std::wstring& value, const std::wstring& translation)
+{
+	lang_string_values_map::iterator it = strings_edit_.begin();
+
+	if(translation.empty())
+	{
+		//If no translation was specified
+		it = strings_edit_.find(default_language_translation); //Find default translation table
+		if(it == strings_edit_.end()) //If there's no default translation table, take the first one
+		{
+			it = strings_edit_.begin();
+			if(it == strings_edit_.end()) //If there's no any translation table, add default one
+			{
+				it = strings_edit_.insert(std::make_pair(default_language_translation, string_values_map())).first;
+				//Also add it to translations list
+				add_translation(default_language_translation);
+			}
+		}
+	}
+	else
+	{
+		it = strings_edit_.find(translation); //Find specified translation table
+		if(it == strings_edit_.end()) //If there's no translation, add it
+		{
+			it = strings_edit_.insert(std::make_pair(translation, string_values_map())).first;
+			//Also add it to translations list
+			add_translation(translation);
+		}
+	}
+
+	//Change value of the required property
+	((*it).second)[property_name] = value;
+}
+
+//Adds translation to translation list
+void version_info_editor::add_translation(const std::wstring& translation)
+{
+	std::pair<uint16_t, uint16_t> translation_ids(translation_from_string(translation));
+	add_translation(translation_ids.first, translation_ids.second);
+}
+
+void version_info_editor::add_translation(uint16_t language_id, uint16_t codepage_id)
+{
+	std::pair<translation_values_map::const_iterator, translation_values_map::const_iterator>
+		range(translations_edit_.equal_range(language_id));
+
+	//If translation already exists
+	for(translation_values_map::const_iterator it = range.first; it != range.second; ++it)
+	{
+		if((*it).second == codepage_id)
+			return;
+	}
+
+	translations_edit_.insert(std::make_pair(language_id, codepage_id));
+}
+
+//Removes translation from translations and strings lists
+void version_info_editor::remove_translation(const std::wstring& translation)
+{
+	std::pair<uint16_t, uint16_t> translation_ids(translation_from_string(translation));
+	remove_translation(translation_ids.first, translation_ids.second);
+}
+
+void version_info_editor::remove_translation(uint16_t language_id, uint16_t codepage_id)
+{
+	{
+		//Erase string table (if exists)
+		std::wstringstream ss;
+		ss << std::hex
+			<< std::setw(4) << std::setfill(L'0') << language_id
+			<< std::setw(4) << std::setfill(L'0') << codepage_id;
+		
+		strings_edit_.erase(ss.str());
+	}
+
+	//Find and erase translation from translations table
+	std::pair<translation_values_map::iterator, translation_values_map::iterator>
+		it_pair = translations_edit_.equal_range(language_id);
+
+	for(translation_values_map::iterator it = it_pair.first; it != it_pair.second; ++it)
+	{
+		if((*it).second == codepage_id)
+		{
+			translations_edit_.erase(it);
+			break;
+		}
+	}
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/version_info_editor.h b/irdb-lib/pebliss/trunk/pe_lib/version_info_editor.h
new file mode 100644
index 0000000000000000000000000000000000000000..2e27d3b28968f044b82da78a62212afb2855bb52
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/version_info_editor.h
@@ -0,0 +1,61 @@
+#ifndef pebliss_version_info_editor_h
+#define pebliss_version_info_editor_h
+#pragma once
+#include "version_info_types.h"
+#include "version_info_viewer.h"
+
+namespace pe_bliss
+{
+	//Helper class to read and edit version information
+	//lang_string_values_map: map of version info strings with encodings
+	//translation_values_map: map of translations
+	class version_info_editor : public version_info_viewer
+	{
+	public:
+		//Default constructor
+		//strings - version info strings with charsets
+		//translations - version info translations map
+		version_info_editor(lang_string_values_map& strings, translation_values_map& translations);
+
+		//Below functions have parameter translation
+		//If it's empty, the default language translation will be taken
+		//If there's no default language translation, the first one will be taken
+
+		//Sets company name
+		void set_company_name(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets file description
+		void set_file_description(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets file version
+		void set_file_version(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets internal file name
+		void set_internal_name(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets legal copyright
+		void set_legal_copyright(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets original file name
+		void set_original_filename(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets product name
+		void set_product_name(const std::wstring& value, const std::wstring& translation = std::wstring());
+		//Sets product version
+		void set_product_version(const std::wstring& value, const std::wstring& translation = std::wstring());
+
+		//Sets version info property value
+		//property_name - property name
+		//value - property value
+		//If translation does not exist, it will be added to strings and translations lists
+		//If property does not exist, it will be added
+		void set_property(const std::wstring& property_name, const std::wstring& value, const std::wstring& translation = std::wstring());
+
+		//Adds translation to translation list
+		void add_translation(const std::wstring& translation);
+		void add_translation(uint16_t language_id, uint16_t codepage_id);
+
+		//Removes translation from translations and strings lists
+		void remove_translation(const std::wstring& translation);
+		void remove_translation(uint16_t language_id, uint16_t codepage_id);
+
+	private:
+		lang_string_values_map& strings_edit_;
+		translation_values_map& translations_edit_;
+	};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/version_info_types.h b/irdb-lib/pebliss/trunk/pe_lib/version_info_types.h
new file mode 100644
index 0000000000000000000000000000000000000000..1525bcf13a4c82f9915eca4abc9770dfd4a7ff4b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/version_info_types.h
@@ -0,0 +1,20 @@
+#ifndef pebliss_version_info_types_h
+#define pebliss_version_info_types_h
+#pragma once
+#include <map>
+#include <string>
+#include "stdint_defs.h"
+
+namespace pe_bliss
+{
+	//Typedef for version info functions: Name - Value
+	typedef std::map<std::wstring, std::wstring> string_values_map;
+	//Typedef for version info functions: Language string - String Values Map
+	//Language String consists of LangID and CharsetID
+	//E.g. 041904b0 for Russian UNICODE, 040004b0 for Process Default Language UNICODE
+	typedef std::map<std::wstring, string_values_map> lang_string_values_map;
+
+	//Typedef for version info functions: Language - Character Set
+	typedef std::multimap<uint16_t, uint16_t> translation_values_map;
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/pe_lib/version_info_viewer.cpp b/irdb-lib/pebliss/trunk/pe_lib/version_info_viewer.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3f6a2573b6b45a85ba28a73c07a954e52f50475d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/version_info_viewer.cpp
@@ -0,0 +1,159 @@
+#include <iomanip>
+#include <sstream>
+#include "pe_exception.h"
+#include "version_info_viewer.h"
+
+namespace pe_bliss
+{
+//Default process language, UNICODE
+const std::wstring version_info_viewer::default_language_translation(L"041904b0");
+
+//Default constructor
+//strings - version info strings with charsets
+//translations - version info translations map
+version_info_viewer::version_info_viewer(const lang_string_values_map& strings, const translation_values_map& translations)
+	:strings_(strings), translations_(translations)
+{}
+
+//Below functions have parameter translation
+//If it's empty, the default language translation will be taken
+//If there's no default language translation, the first one will be taken
+
+//Returns company name
+const std::wstring version_info_viewer::get_company_name(const std::wstring& translation) const
+{
+	return get_property(L"CompanyName", translation);
+}
+
+//Returns file description
+const std::wstring version_info_viewer::get_file_description(const std::wstring& translation) const
+{
+	return get_property(L"FileDescription", translation);
+}
+
+//Returns file version
+const std::wstring version_info_viewer::get_file_version(const std::wstring& translation) const
+{
+	return get_property(L"FileVersion", translation);
+}
+
+//Returns internal file name
+const std::wstring version_info_viewer::get_internal_name(const std::wstring& translation) const
+{
+	return get_property(L"InternalName", translation);
+}
+
+//Returns legal copyright
+const std::wstring version_info_viewer::get_legal_copyright(const std::wstring& translation) const
+{
+	return get_property(L"LegalCopyright", translation);
+}
+
+//Returns original file name
+const std::wstring version_info_viewer::get_original_filename(const std::wstring& translation) const
+{
+	return get_property(L"OriginalFilename", translation);
+}
+
+//Returns product name
+const std::wstring version_info_viewer::get_product_name(const std::wstring& translation) const
+{
+	return get_property(L"ProductName", translation);
+}
+
+//Returns product version
+const std::wstring version_info_viewer::get_product_version(const std::wstring& translation) const
+{
+	return get_property(L"ProductVersion", translation);
+}
+
+//Returns list of translations in string representation
+const version_info_viewer::translation_list version_info_viewer::get_translation_list() const
+{
+	translation_list ret;
+
+	//Enumerate all translations
+	for(translation_values_map::const_iterator it = translations_.begin(); it != translations_.end(); ++it)
+	{
+		//Create string representation of translation value
+		std::wstringstream ss;
+		ss << std::hex
+			<< std::setw(4) << std::setfill(L'0') << (*it).first
+			<< std::setw(4) << std::setfill(L'0') <<  (*it).second;
+
+		//Save it
+		ret.push_back(ss.str());
+	}
+
+	return ret;
+}
+
+//Returns version info property value
+//property_name - required property name
+//If throw_if_absent = true, will throw exception if property does not exist
+//If throw_if_absent = false, will return empty string if property does not exist
+const std::wstring version_info_viewer::get_property(const std::wstring& property_name, const std::wstring& translation, bool throw_if_absent) const
+{
+	std::wstring ret;
+
+	//If there're no strings
+	if(strings_.empty())
+	{
+		if(throw_if_absent)
+			throw pe_exception("Version info string does not exist", pe_exception::version_info_string_does_not_exist);
+
+		return ret;
+	}
+	
+	lang_string_values_map::const_iterator it = strings_.begin();
+
+	if(translation.empty())
+	{
+		//If no translation was specified
+		it = strings_.find(default_language_translation); //Find default translation table
+		if(it == strings_.end()) //If there's no default translation table, take the first one
+			it = strings_.begin();
+	}
+	else
+	{
+		it = strings_.find(translation); //Find specified translation table
+		if(it == strings_.end())
+		{
+			if(throw_if_absent)
+				throw pe_exception("Version info string does not exist", pe_exception::version_info_string_does_not_exist);
+
+			return ret;
+		}
+	}
+	
+	//Find value of the required property
+	string_values_map::const_iterator str_it = (*it).second.find(property_name);
+
+	if(str_it == (*it).second.end())
+	{
+		if(throw_if_absent)
+			throw pe_exception("Version info string does not exist", pe_exception::version_info_string_does_not_exist);
+
+		return ret;
+	}
+
+	ret = (*str_it).second;
+
+	return ret;
+}
+
+//Converts translation HEX-string to pair of language ID and codepage ID
+const version_info_viewer::translation_pair version_info_viewer::translation_from_string(const std::wstring& translation)
+{
+	uint32_t translation_id = 0;
+
+	{
+		//Convert string to DWORD
+		std::wstringstream ss;
+		ss << std::hex << translation;
+		ss >> translation_id;
+	}
+
+	return std::make_pair(static_cast<uint16_t>(translation_id >> 16), static_cast<uint16_t>(translation_id & 0xFFFF));
+}
+}
diff --git a/irdb-lib/pebliss/trunk/pe_lib/version_info_viewer.h b/irdb-lib/pebliss/trunk/pe_lib/version_info_viewer.h
new file mode 100644
index 0000000000000000000000000000000000000000..c859d49b83fef7bac5e4a918a1fcc9945925c127
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/pe_lib/version_info_viewer.h
@@ -0,0 +1,71 @@
+#ifndef pebliss_version_info_viewer_h
+#define pebliss_version_info_viewer_h
+#pragma once
+#include <map>
+#include <vector>
+#include <string>
+#include "pe_resource_viewer.h"
+#include "pe_structures.h"
+#include "version_info_types.h"
+
+namespace pe_bliss
+{
+//Helper class to read version information
+//lang_string_values_map: map of version info strings with encodings
+//translation_values_map: map of translations
+class version_info_viewer
+{
+public:
+	//Useful typedefs
+	typedef std::pair<uint16_t, uint16_t> translation_pair;
+	typedef std::vector<std::wstring> translation_list;
+
+public:
+	//Default constructor
+	//strings - version info strings with charsets
+	//translations - version info translations map
+	version_info_viewer(const lang_string_values_map& strings, const translation_values_map& translations);
+
+	//Below functions have parameter translation
+	//If it's empty, the default language translation will be taken
+	//If there's no default language translation, the first one will be taken
+
+	//Returns company name
+	const std::wstring get_company_name(const std::wstring& translation = std::wstring()) const;
+	//Returns file description
+	const std::wstring get_file_description(const std::wstring& translation = std::wstring()) const;
+	//Returns file version
+	const std::wstring get_file_version(const std::wstring& translation = std::wstring()) const;
+	//Returns internal file name
+	const std::wstring get_internal_name(const std::wstring& translation = std::wstring()) const;
+	//Returns legal copyright
+	const std::wstring get_legal_copyright(const std::wstring& translation = std::wstring()) const;
+	//Returns original file name
+	const std::wstring get_original_filename(const std::wstring& translation = std::wstring()) const;
+	//Returns product name
+	const std::wstring get_product_name(const std::wstring& translation = std::wstring()) const;
+	//Returns product version
+	const std::wstring get_product_version(const std::wstring& translation = std::wstring()) const;
+
+	//Returns list of translations in string representation
+	const translation_list get_translation_list() const;
+
+	//Returns version info property value
+	//property_name - required property name
+	//If throw_if_absent = true, will throw exception if property does not exist
+	//If throw_if_absent = false, will return empty string if property does not exist
+	const std::wstring get_property(const std::wstring& property_name, const std::wstring& translation = std::wstring(), bool throw_if_absent = false) const;
+
+	//Converts translation HEX-string to pair of language ID and codepage ID
+	static const translation_pair translation_from_string(const std::wstring& translation);
+
+public:
+	//Default process language, UNICODE
+	static const std::wstring default_language_translation;
+
+private:
+	const lang_string_values_map& strings_;
+	const translation_values_map& translations_;
+};
+}
+#endif
diff --git a/irdb-lib/pebliss/trunk/samples/Makefile b/irdb-lib/pebliss/trunk/samples/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..c2502b105bb9f924f017e2fce514bc0b2ca526e6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/Makefile
@@ -0,0 +1,18 @@
+SAMPLES = address_convertions basic_dotnet_viewer basic_info_viewer bound_import_reader debug_info_reader entropy_calculator exception_dir_reader export_adder exports_reader full_pe_rebuilder image_config_editor import_adder imports_reader pe_config_reader pe_realigner pe_rebaser pe_sections_reader pe_stripper relocation_adder relocations_reader resource_editor resource_viewer rich_overlay_stub_reader section_adder sections_and_addresses tls_editor tls_reader
+OUTDIR = ./out/
+LIBPATH = ../lib/libpebliss.a
+TARGETS = $(foreach sample,$(SAMPLES),$(sample)_sample)
+TARGETS_CLEAN = $(foreach sample,$(SAMPLES),$(sample)_clean)
+
+all: $(TARGETS)
+
+clean: $(TARGETS_CLEAN)
+
+$(OUTDIR):
+	mkdir -p $(OUTDIR)
+
+%_sample: $(OUTDIR) $(LIBPATH)
+	$(MAKE) PE_DEBUG=$(PE_DEBUG) -C ./$*
+	
+%_clean:
+	$(MAKE) -C ./$* clean
diff --git a/irdb-lib/pebliss/trunk/samples/address_convertions/Makefile b/irdb-lib/pebliss/trunk/samples/address_convertions/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/address_convertions/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcproj b/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..146d0a5779034cdaadf7f7c73e621ee9c7d761e2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="address_convertions"
+	ProjectGUID="{642392B3-C763-44C8-91F4-EA90C3651608}"
+	RootNamespace="address_convertions"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcxproj b/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..4ad28fd6f65da9a4e4b346838ca6dd99f05c2683
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{2754B0D6-4A8B-49F4-AB9E-E7306D0DAB32}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>address_convertions</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/address_convertions/address_convertions.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/address_convertions/main.cpp b/irdb-lib/pebliss/trunk/samples/address_convertions/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..cd2f88781121ee8fdd528e7697507dba509f5865
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/address_convertions/main.cpp
@@ -0,0 +1,55 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как конвертировать адреса для PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: address_convertions.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Получаем список секций
+		std::cout << "Reading PE sections..." << std::hex << std::showbase << std::endl << std::endl;
+		const section_list sections = image.get_image_sections();
+
+		//Перечисляем секции и выводим информацию о них
+		for(section_list::const_iterator it = sections.begin(); it != sections.end(); ++it)
+		{
+			const section& s = *it; //Секция
+			std::cout << "Section [" << s.get_name() << "]" << std::endl //Имя секции
+				<< " -> RVA: " << s.get_virtual_address() << std::endl //Виртуальный адрес (RVA)
+				<< " -> VA: " << image.rva_to_va_64(s.get_virtual_address()) << std::endl //Виртуальный адрес (VA)
+				<< " -> File offset: " << image.rva_to_file_offset(s.get_virtual_address()) //Файловое смещение секции, вычисленное из ее RVA
+				<< std::endl << std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/Makefile b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcproj b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..7cee484943d3aeea8e07aea492a9e18fb2424ac8
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="basic_dotnet_viewer"
+	ProjectGUID="{DE053D44-F9BD-4C1A-B44B-3157BE27AD02}"
+	RootNamespace="basic_dotnet_viewer"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcxproj b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..7e0c09fa7c3d3b7539b92a7527f62e86f5a3e18d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{5E2C4403-4C8B-4773-89A6-61547756ABDC}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>basic_dotnet_viewer</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/basic_dotnet_viewer.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/main.cpp b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..20ddd66a61a45461b76db3477a5e17dd442f7243
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_dotnet_viewer/main.cpp
@@ -0,0 +1,69 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как получить базовую информацию о .NET PE-файле
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: basic_dotnet_viewer.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Если образ не .NET, выходим
+		if(!image.is_dotnet())
+		{
+			std::cout << "Image is not .NET" << std::endl;
+			return 0;
+		}
+		
+		std::cout << "Reading basic dotnet info..." << std::hex << std::showbase << std::endl << std::endl;
+		
+		//Получаем .NET-заголовок PE-файла
+		const basic_dotnet_info info(get_basic_dotnet_info(image));
+
+		//Выводим некоторую информацию
+		std::cout << "Major runtime version: " << info.get_major_runtime_version() << std::endl //Версия рантайма
+			<< "Minor runtime version: " << info.get_minor_runtime_version() << std::endl
+			<< "Flags: " << info.get_flags() << std::endl //Флаги
+			<< "RVA of resources: " << info.get_rva_of_resources() << std::endl //RVA ресурсов
+			<< "RVA of metadata: " << info.get_rva_of_metadata() << std::endl //RVA метаданных
+			<< "Size of resources: " << info.get_size_of_resources() << std::endl //Размер ресурсов
+			<< "Size of metadata: " << info.get_size_of_metadata() << std::endl; //Размер метаданных
+
+		//Определим точку входа .NET
+		if(info.is_native_entry_point())
+			std::cout << "Entry point RVA: ";
+		else
+			std::cout << "Entry point token: ";
+
+		std::cout << info.get_entry_point_rva_or_token() << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/basic_info_viewer/Makefile b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcproj b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..6cb615b2bee59d71cc0987adfb3f105b7209c3c5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="basic_info_viewer"
+	ProjectGUID="{7AF45D7B-8341-42CF-B382-B67E1399D8B1}"
+	RootNamespace="basic_info_viewer"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcxproj b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..77e9a7d80f1353050946bc819b4b4aacf65d7c18
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{71707667-1A10-4B53-AC02-E4AD898AC6E7}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>basic_info_viewer</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/basic_info_viewer.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/basic_info_viewer/main.cpp b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..32573d922ada6a9f5108c1b7203b39240d27aeb3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/basic_info_viewer/main.cpp
@@ -0,0 +1,82 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как получить базовую информацию о PE-файле
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: basic_info_viewer.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Фабрика автоматически получает тип PE-файла и создает экземпляр нужного класса,
+		//но можно получить тип PE-файла и вручную, воспользовавшись одной из перегрузок функции get_pe_type
+		//Здесь мы просто выведем уже известный тип PE-файла:
+		std::cout << "PE file type: " << (image.get_pe_type() == pe_type_32 ? "PE32 (PE)" : "PE64 (PE+)") << std::endl;
+		
+		//Вычислим контрольную сумму PE-файла
+		std::cout << "Calculated checksum: "<< std::hex << std::showbase << calculate_checksum(pe_file) << std::endl;
+		//Выведем контрольную сумму из заголовка файла (для не-драйверов она обычно равна 0)
+		std::cout << "Stored checksum: " << image.get_checksum() << std::endl;
+
+		//Выведем характеристики PE-файла
+		std::cout << "Characteristics: " << image.get_characteristics() << std::endl;
+		
+		//Выведем адрес точки входа
+		std::cout << "Entry point: " << image.get_ep() << std::endl;
+		
+		//Выведем выравнивание
+		std::cout << "File alignment: " << image.get_file_alignment() << std::endl;
+		std::cout << "Section alignment: " << image.get_section_alignment() << std::endl;
+		
+		//Выведем базу образа в 64-битном виде (универсально для PE и PE+)
+		std::cout << "Image base: " << image.get_image_base_64() << std::endl;
+		
+		//Выведем подсистему
+		std::cout << "Subsystem: " << image.get_subsystem() << std::endl;
+		std::cout << "Is console: " << (image.is_console() ? "YES" : "NO") << std::endl;
+		std::cout << "Is windows GUI: " << (image.is_gui() ? "YES" : "NO") << std::endl;
+		
+		//Выведем, какие директории есть у файла
+		std::cout << "Has bound import: " << (image.has_bound_import() ? "YES" : "NO") << std::endl;
+		std::cout << "Has config: " << (image.has_config() ? "YES" : "NO") << std::endl;
+		std::cout << "Has debug: " << (image.has_debug() ? "YES" : "NO") << std::endl;
+		std::cout << "Has delay import: " << (image.has_delay_import() ? "YES" : "NO") << std::endl;
+		std::cout << "Has exception directory: " << (image.has_exception_directory() ? "YES" : "NO") << std::endl;
+		std::cout << "Has exports: " << (image.has_exports() ? "YES" : "NO") << std::endl;
+		std::cout << "Has imports: " << (image.has_imports() ? "YES" : "NO") << std::endl;
+		std::cout << "Has reloc: " << (image.has_reloc() ? "YES" : "NO") << std::endl;
+		std::cout << "Has resources: " << (image.has_resources() ? "YES" : "NO") << std::endl;
+		std::cout << "Has security: " << (image.has_security() ? "YES" : "NO") << std::endl;
+		std::cout << "Has tls: " << (image.has_tls() ? "YES" : "NO") << std::endl;
+		std::cout << "Is .NET: " << (image.is_dotnet() ? "YES" : "NO") << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/bound_import_reader/Makefile b/irdb-lib/pebliss/trunk/samples/bound_import_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/bound_import_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcproj b/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..b50c696393be17a9fea98657979f338173fb26a4
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="bound_import_reader"
+	ProjectGUID="{65229ACC-5C9B-429C-B9DA-4710697637EB}"
+	RootNamespace="bound_import_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..9ab4f6be16a61802a71e3c9d1affd0cb4cb5fed1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{EFC31F33-D5E4-4356-A892-18CADABCFCCF}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>bound_import_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/bound_import_reader/bound_import_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/bound_import_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/bound_import_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..bdd119de7d4bc77c0c977471e378b5f32ecb4b54
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/bound_import_reader/main.cpp
@@ -0,0 +1,68 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию о привязанном импорте PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: bound_import_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Проверим, есть ли привязанный импорт у PE-файла
+		if(!image.has_bound_import())
+		{
+			std::cout << "Image has no bound import" << std::endl;
+			return 0;
+		}
+
+		std::cout << "Reading PE bound import..." << std::hex << std::showbase << std::endl << std::endl;
+		
+		//Получаем информацию о привязанном импорте
+		const bound_import_module_list modules(get_bound_import_module_list(image));
+
+		//Выведем импортируемые модули и форварды
+		for(bound_import_module_list::const_iterator it = modules.begin(); it != modules.end(); ++it)
+		{
+			const bound_import& import = *it; //Импортируемая библиотека
+			std::cout << "Module: " << import.get_module_name() << std::endl //Имя модуля
+				<< "Timestamp: " << import.get_timestamp() << std::endl; //Временная метка
+
+			//Перечислим форварды для модуля - модули, на которые ссылается этот:
+			const bound_import::ref_list& refs = import.get_module_ref_list();
+			for(bound_import::ref_list::const_iterator ref_it = refs.begin(); ref_it != refs.end(); ++ref_it)
+			{
+				std::cout << " -> Module: " << (*ref_it).get_module_name() << std::endl //Имя модуля, на который ссылается родительский модуль
+					<< " -> Timestamp: " << (*ref_it).get_timestamp() << std::endl; //Временная метка
+			}
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/debug_info_reader/Makefile b/irdb-lib/pebliss/trunk/samples/debug_info_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/debug_info_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcproj b/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..4a462be617a8eec5d3819e0a759f4a9519fdf2cd
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="debug_info_reader"
+	ProjectGUID="{218033A7-A6D0-45B4-88F6-F4FF5DD25207}"
+	RootNamespace="debug_info_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..391d23d4e814531e3ace2a8617effd8877361baf
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{332A1418-E89B-4658-9F7F-8D219ED776EA}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>debug_info_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/debug_info_reader/debug_info_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/debug_info_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/debug_info_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a157f0ad06964f84b4bad7b1b9b65f27aa86c554
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/debug_info_reader/main.cpp
@@ -0,0 +1,191 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и обработать отладочную информацию PE или PE+ файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: debug_info_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Проверим, есть ли отладочная информация у файла
+		if(!image.has_debug())
+		{
+			std::cout << "Image has no debug information" << std::endl;
+			return 0;
+		}
+
+		std::cout << "Reading PE debug information..." << std::hex << std::showbase << std::endl << std::endl;
+
+		//Получаем отладочную информацию, находящуюся в PE-файле
+		const debug_info_list info_list(get_debug_information(image));
+		
+		//Перечисоляем все отладочные записи
+		for(debug_info_list::const_iterator it = info_list.begin(); it != info_list.end(); ++it)
+		{
+			const debug_info& info = *it;
+
+			//Выведем тип отладочной информации
+			std::cout << "Debug info type: ";
+			switch(info.get_type())
+			{
+			case debug_info::debug_type_borland:
+				std::cout << "Borland";
+				break;
+
+			case debug_info::debug_type_clsid:
+				std::cout << "CLSID";
+				break;
+
+			case debug_info::debug_type_codeview:
+				std::cout << "CodeView";
+				break;
+
+			case debug_info::debug_type_coff:
+				std::cout << "COFF";
+				break;
+
+			case debug_info::debug_type_exception:
+				std::cout << "Exception";
+				break;
+
+			case debug_info::debug_type_fixup:
+				std::cout << "Fixup";
+				break;
+
+			case debug_info::debug_type_fpo:
+				std::cout << "FPO";
+				break;
+
+			case debug_info::debug_type_misc:
+				std::cout << "Misc";
+				break;
+
+			case debug_info::debug_type_omap_from_src:
+				std::cout << "OMAP from src";
+				break;
+
+			case debug_info::debug_type_omap_to_src:
+				std::cout << "OMAP to src";
+				break;
+
+			default:
+				std::cout << "Unknown";
+			}
+
+			std::cout << std::endl;
+
+			std::cout << "Timestamp: " << info.get_time_stamp() << std::endl << std::endl; //Временная метка
+
+			//Получим дополнительную информацию, если таковая имеется
+			switch(info.get_advanced_info_type())
+			{
+			case debug_info::advanced_info_pdb_7_0:
+				{
+					std::cout << "Advanced info - PDB 7.0" << std::endl; //PDB 7.0
+					pdb_7_0_info advanced = info.get_advanced_debug_info<pdb_7_0_info>();
+					std::cout << "PDB file name: " << advanced.get_pdb_file_name() << std::endl; //Имя файла PDB
+					std::cout << "Age: " << advanced.get_age() << std::endl; //Возраст (билд)
+				}
+				break;
+
+			case debug_info::advanced_info_pdb_2_0:
+				{
+					std::cout << "Advanced info - PDB 2.0" << std::endl; //PDB 2.0
+					pdb_2_0_info advanced = info.get_advanced_debug_info<pdb_2_0_info>();
+					std::cout << "PDB file name: " << advanced.get_pdb_file_name() << std::endl; //Имя файла PDB
+					std::cout << "Age: " << advanced.get_age() << std::endl; //Возраст (билд)
+				}
+				break;
+
+			case debug_info::advanced_info_misc:
+				{
+					std::cout << "Advanced info - Misc" << std::endl; //Misc
+					misc_debug_info advanced = info.get_advanced_debug_info<misc_debug_info>();
+					std::cout << "Advanced data is EXE name: " << (advanced.is_exe_name() ? "YES" : "NO") << std::endl; //Если данные в структуре - имя EXE-файла
+
+					//Выведем строковые данные
+					if(advanced.is_unicode())
+						std::wcout << advanced.get_data_unicode() << std::endl;
+					else
+						std::cout << advanced.get_data_ansi() << std::endl;
+				}
+				break;
+
+			case debug_info::advanced_info_coff:
+				{
+					std::cout << "Advanced info - COFF" << std::endl; //COFF
+					coff_debug_info advanced = info.get_advanced_debug_info<coff_debug_info>();
+					std::cout << "LVA to first line number: " << advanced.get_lva_to_first_line_number() << std::endl; //Адрес первого элемента в массиве номеров строк
+					std::cout << "LVA to first symbol: " << advanced.get_lva_to_first_symbol() << std::endl; //Адрес первого элемента в массиве символов
+					std::cout << "Number of line numbers: " << advanced.get_number_of_line_numbers() << std::endl; //Количество номеров строк
+					std::cout << "Number of symbols: " << advanced.get_number_of_symbols() << std::endl; //Количество номеров строк
+					std::cout << "RVA of first byte of code: " << advanced.get_rva_to_first_byte_of_code() << std::endl; //RVA первого байта кода
+					std::cout << "RVA of first byte of data: " << advanced.get_rva_to_first_byte_of_data() << std::endl; //RVA первого байта данных
+					std::cout << "RVA of last byte of code " << advanced.get_rva_to_last_byte_of_code() << std::endl; //RVA последнего байта кода
+					std::cout << "RVA of last byte of data: " << advanced.get_rva_to_last_byte_of_data() << std::endl; //RVA последнего байта данных
+
+					std::cout << std::endl << "Symbol list:" << std::endl;
+
+					//Получим список символов
+					const coff_debug_info::coff_symbols_list& symbols = advanced.get_symbols();
+					for(coff_debug_info::coff_symbols_list::const_iterator symbol_it = symbols.begin(); symbol_it != symbols.end(); ++symbol_it)
+					{
+						//Выведем информацию об отладочных символах
+						const coff_debug_info::coff_symbol& symbol = *symbol_it; //Отладочный символ
+						std::cout << "Index: " << symbol.get_index() << std::endl
+							<< "RVA: " << symbol.get_rva() << std::endl
+							<< "Section number: " << symbol.get_section_number() << std::endl
+							<< "Storage class: " << symbol.get_storage_class() << std::endl
+							<< "Type: " << symbol.get_type() << std::endl
+							<< "Is file: " << (symbol.is_file() ? "YES" : "NO") << std::endl
+							<< "Symbol: " << symbol.get_symbol() << std::endl << std::endl;
+					}
+				}
+				break;
+
+			case debug_info::advanced_info_codeview_4_0:
+				std::cout << "Advanced info - CodeView 4.0" << std::endl; //CodeView 4.0
+				break;
+
+			case debug_info::advanced_info_codeview_5_0:
+				std::cout << "Advanced info - CodeView 5.0" << std::endl; //CodeView 5.0
+				break;
+				
+			default:
+				break;
+			}
+
+			std::cout << std::endl << "==========" << std::endl << std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/entropy_calculator/Makefile b/irdb-lib/pebliss/trunk/samples/entropy_calculator/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/entropy_calculator/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcproj b/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..aad775d02469766280cf65203586b1bd181361d0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="entropy_calculator"
+	ProjectGUID="{111344DB-1F0B-460E-91DD-9DD36D2238A4}"
+	RootNamespace="entropy_calculator"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcxproj b/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..2fe9def4e9fe6a88fe2877254a00eecabb9ea4b7
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{48879460-0DF8-491E-BD1D-A489C8D92746}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>entropy_calculator</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/entropy_calculator/entropy_calculator.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/entropy_calculator/main.cpp b/irdb-lib/pebliss/trunk/samples/entropy_calculator/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3f7a1660f5fc2e7827bf9db44e65758e321aa7c6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/entropy_calculator/main.cpp
@@ -0,0 +1,54 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как посчитать энтропию файла и секций PE
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: entropy_calculator.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+
+	try
+	{
+		//Считаем энтропию файла
+		std::cout << "File entropy: " << entropy_calculator::calculate_entropy(pe_file) << std::endl;
+
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		std::cout << "Sections entropy: " << entropy_calculator::calculate_entropy(image) << std::endl; //Считаем энтропию всех секций
+
+		//Перечисляем секции и считаем их энтропию по отдельности
+		const section_list sections = image.get_image_sections();
+		for(section_list::const_iterator it = sections.begin(); it != sections.end(); ++it)
+		{
+			if(!(*it).empty()) //Если секция не пуста - посчитаем ее энтропию
+				std::cout << "Section [" << (*it).get_name() << "] entropy: " << entropy_calculator::calculate_entropy(*it) << std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/exception_dir_reader/Makefile b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcproj b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..28f0fd5487e7993ceff6850a62b4eeaedfe8ddf1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="exception_dir_reader"
+	ProjectGUID="{D8E2714A-11A7-478D-A966-EF6968FFB766}"
+	RootNamespace="exception_dir_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..b1f0c53dd6e885ca0405bd10d29c39d0c672aff4
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{EFAF41AB-C77D-4819-996E-4F6C305553A5}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>exception_dir_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/exception_dir_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/exception_dir_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..8a29d35cad0276532f2dc4197c8b981c1ff6e67a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exception_dir_reader/main.cpp
@@ -0,0 +1,71 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию о директории исключений
+//Она существует только для 64-разрядных PE-файлов (PE+)
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: exception_dir_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Проверим, есть ли директория информации об исключениях у PE-файла
+		if(!image.has_exception_directory())
+		{
+			std::cout << "Image has no exception directory" << std::endl;
+			return 0;
+		}
+
+		std::cout << "Reading exception directory..." << std::hex << std::showbase << std::endl << std::endl;
+		
+		//Получаем информацию из exception directory
+		const exception_entry_list info(get_exception_directory_data(image));
+
+		//Выведем записи из exception directory
+		//Подробное описание всех этих структур есть в MSDN
+		for(exception_entry_list::const_iterator it = info.begin(); it != info.end(); ++it)
+		{
+			const exception_entry& entry = *it; //Запись из таблицы
+
+			//Выведем информацию
+			std::cout << "Addresses: [" << entry.get_begin_address() << ":" << entry.get_end_address() << "]:" << std::endl
+				<< "Flags: " << static_cast<unsigned long>(entry.get_flags()) << std::endl
+				<< "Frame pointer register number: " << static_cast<unsigned long>(entry.get_frame_pointer_register_number()) << std::endl
+				<< "Number of unwind slots: " << static_cast<unsigned long>(entry.get_number_of_unwind_slots()) << std::endl
+				<< "Scaled RSP offset: " << static_cast<unsigned long>(entry.get_scaled_rsp_offset()) << std::endl
+				<< "Size of prolog: " << static_cast<unsigned long>(entry.get_size_of_prolog()) << std::endl
+				<< "Unwind info address: " << entry.get_unwind_info_address() << std::endl
+				<< "Unwind info version: " << static_cast<unsigned long>(entry.get_unwind_info_version()) << std::endl
+				<< std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/export_adder/Makefile b/irdb-lib/pebliss/trunk/samples/export_adder/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/export_adder/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcproj b/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..2579b13f22c32669107a2c2131a1499ba1da1d01
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="export_adder"
+	ProjectGUID="{4459EB9F-0332-46C4-BF60-6CECA73C7D17}"
+	RootNamespace="export_adder"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcxproj b/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..6cec6d1b85e2bc7da79c99adf4db88483645def7
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{17C01A93-C7F0-49EB-A9A0-81F5E06779C3}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>export_adder</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/export_adder/export_adder.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/export_adder/main.cpp b/irdb-lib/pebliss/trunk/samples/export_adder/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..c7aacbff57a9d166945df209795d86eb69481248
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/export_adder/main.cpp
@@ -0,0 +1,101 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как добавить новый экспорт в таблицу экспорта PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: export_adder.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Получим список экспортируемых функций и информацию об экспорте
+		export_info info;
+		exported_functions_list exports;
+
+		//Если экспортов у файла нет, этот вызов бросит исключение, но это не значит, что мы
+		//не можем создать таблицу экспортов с нуля
+		try
+		{
+			exports = get_exported_functions(image, info);
+		}
+		catch(const pe_exception&)
+		{
+			//Нет таблицы экспортов, или она кривая
+			//Создадим информацию об экспортах вручную
+			info.set_name("MySuperLib.dll");
+			info.set_ordinal_base(5);
+		}
+
+		//Создаем новую экспортируемую функцию
+		exported_function func;
+		func.set_name("SuperKernelCall"); //Имя экспортируемой функции
+		func.set_rva(0x123); //Относительный адрес точки входа экспортируемой функции (некорректный, чисто для примера)
+
+		//Необходимо вычислить ординал функции, которую мы добавляем, чтобы не было повторных
+		//Для этого есть вспомогательная функция
+		func.set_ordinal(get_export_ordinal_limits(exports).second + 1); //Сделаем наш ординал = максимальный ординал среди существующих экспортов + 1
+		exports.push_back(func); //Добавим функцию к экспортам
+		
+		//Можно редактировать и существующие экспорты
+		//или изменить информацию об экспортах (info)
+		//Но мы просто пересоберем таблицу экспортов
+		//Она будет иметь больший размер, чем до нашего редактирования,
+		//поэтому запишем ее в новую секцию, чтобы все поместилось
+		//(мы не можем расширять существующие секции, если только секция не в самом конце файла)
+		section new_exports;
+		new_exports.get_raw_data().resize(1); //Мы не можем добавлять пустые секции, поэтому пусть у нее будет начальный размер данных 1
+		new_exports.set_name("new_exp"); //Имя секции
+		new_exports.readable(true); //Доступна на чтение
+		section& attached_section = image.add_section(new_exports); //Добавим секцию и получим ссылку на добавленную секцию с просчитанными размерами
+
+		rebuild_exports(image, info, exports, attached_section); //Пересобираем экспорты, расположив их с начала новой секции и записав новые данные таблиц экспорта в PE-заголовок
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/exports_reader/Makefile b/irdb-lib/pebliss/trunk/samples/exports_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exports_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcproj b/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..c82d6c85b739f63c7f68cc5241b77f48c3e72265
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="exports_reader"
+	ProjectGUID="{AC7C3A84-2F81-4B22-B27E-50A9D4C750E2}"
+	RootNamespace="exports_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..bce82ae68f41755162866d417c2516c6679abc17
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{32ABD41F-7BCE-43E0-853E-21E16260EDB7}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>exports_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exports_reader/exports_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/exports_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/exports_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..dba289971a0eda42342b16c34e6b2a5af0cfbcb7
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/exports_reader/main.cpp
@@ -0,0 +1,78 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию об экспортах PE или PE+ файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: exports_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Проверим, есть ли экспорты у PE-файла
+		if(!image.has_exports())
+		{
+			std::cout << "Image has no exports" << std::endl;
+			return 0;
+		}
+
+		std::cout << "Reading PE exports..." << std::hex << std::showbase << std::endl << std::endl;
+		
+		//Получаем полную информацию об экспортах и список экспортируемых функций
+		export_info info;
+		const exported_functions_list exports = get_exported_functions(image, info);
+
+		//Выведем некоторую информацию об экспорте:
+		std::cout << "Export info" << std::endl
+			<< "Library name: " << info.get_name() << std::endl //Имя библиотеки
+			<< "Timestamp: " << info.get_timestamp() << std::endl //Временная метка
+			<< "Ordinal base: " << info.get_ordinal_base() << std::endl //База ординалов
+			<< std::endl;
+
+		//Перечисляем секции и выводим информацию о них
+		for(exported_functions_list::const_iterator it = exports.begin(); it != exports.end(); ++it)
+		{
+			const exported_function& func = *it; //Экспортируемая функция
+			std::cout << "[+] ";
+			if(func.has_name()) //Если функция имеет имя, выведем его и ординал имени
+				std::cout << func.get_name() << ", name ordinal: " << func.get_name_ordinal() << " ";
+
+			//Ординал функции
+			std::cout << "ORD: " << func.get_ordinal();
+			
+			//Если функция - форвард (переадресация в другую DLL), выведем имя форварда
+			if(func.is_forwarded())
+				std::cout << std::endl << " -> " << func.get_forwarded_name();
+
+			std::cout << std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/Makefile b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcproj b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..5ea82bbe961a33d0f052ff9a02b03c77c3ea41c1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="full_pe_rebuilder"
+	ProjectGUID="{F61AB18A-8E8B-43D1-91B2-D6A2A297FDD6}"
+	RootNamespace="full_pe_rebuilder"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcxproj b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..06536189d4688632d5889ea505eca9eda76a7f36
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcxproj
@@ -0,0 +1,154 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{D7F6EE93-F88A-4B66-8761-87EC844E20C5}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>full_pe_rebuilder</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/full_pe_rebuilder.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/main.cpp b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b5922babe4904a2fc7f84af9ed04d53bc214206a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/full_pe_rebuilder/main.cpp
@@ -0,0 +1,109 @@
+#include <iostream>
+#include <fstream>
+#include <sstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как с нуля создать PE-файл
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: full_pe_rebuilder.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Новый образ, который мы создадим из открытого с нуля
+		std::auto_ptr<pe_base> new_image;
+
+		{
+			//Создаем экземпляр PE или PE+ класса с помощью фабрики
+			pe_base image(pe_factory::create_pe(pe_file));
+
+			//Создаем новый пустой образ
+			new_image.reset(image.get_pe_type() == pe_type_32
+				? static_cast<pe_base*>(new pe_base(pe_properties_32(), image.get_section_alignment()))
+				: static_cast<pe_base*>(new pe_base(pe_properties_64(), image.get_section_alignment())));
+
+			//Копируем важные параметры старого образа в новый
+			new_image->set_characteristics(image.get_characteristics());
+			new_image->set_dll_characteristics(image.get_dll_characteristics());
+			new_image->set_file_alignment(image.get_file_alignment());
+			new_image->set_heap_size_commit(image.get_heap_size_commit_64());
+			new_image->set_heap_size_reserve(image.get_heap_size_reserve_64());
+			new_image->set_stack_size_commit(image.get_stack_size_commit_64());
+			new_image->set_stack_size_reserve(image.get_stack_size_reserve_64());
+			new_image->set_image_base_64(image.get_image_base_64());
+			new_image->set_ep(image.get_ep());
+			new_image->set_number_of_rvas_and_sizes(new_image->get_number_of_rvas_and_sizes());
+			new_image->set_subsystem(image.get_subsystem());
+
+			//Копируем все существующие директории
+			for(unsigned long i = 0; i < image.get_number_of_rvas_and_sizes(); ++i)
+			{
+				new_image->set_directory_rva(i, image.get_directory_rva(i));
+				new_image->set_directory_size(i, image.get_directory_size(i));
+			}
+
+			//Копируем данные секций
+			{
+				const section_list& pe_sections = image.get_image_sections();
+				for(section_list::const_iterator it = pe_sections.begin(); it != pe_sections.end(); ++it)
+					new_image->set_section_virtual_size(new_image->add_section(*it), (*it).get_virtual_size());
+			}
+		}
+
+
+		//Просчитаем контрольную сумму нового PE-файла
+		//и сохраним ее (для примера)
+		{
+			std::stringstream temp_pe(std::ios::out | std::ios::in | std::ios::binary);
+			rebuild_pe(*new_image, temp_pe);
+			new_image->set_checksum(calculate_checksum(temp_pe));
+		}
+
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		new_image->set_stub_overlay("alalalalala alalalala!!! alalalala alalalalalala!!!!!!");
+
+		//Пересобираем PE-файл из нового обраща
+		rebuild_pe(*new_image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/image_config_editor/Makefile b/irdb-lib/pebliss/trunk/samples/image_config_editor/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/image_config_editor/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcproj b/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..7296d74716c1e587dd38cda99b2fc44bc682feec
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="image_config_editor"
+	ProjectGUID="{22788F46-AB6B-4278-B1C0-ED220AE85F4A}"
+	RootNamespace="image_config_editor"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcxproj b/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..777d961c811f663da3f0e0331a646c501a44844b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcxproj
@@ -0,0 +1,154 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{48B99169-44E6-41E5-A681-78243B885E86}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>image_config_editor</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/image_config_editor/image_config_editor.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/image_config_editor/main.cpp b/irdb-lib/pebliss/trunk/samples/image_config_editor/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..09cf4187d5a4b2b15a609e9f961825a0287026b3
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/image_config_editor/main.cpp
@@ -0,0 +1,82 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как пересобрать директорию Load Config у PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: image_config_editor.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Получим информацию о директории Load Config
+		image_config_info info(get_image_config(image));
+
+		//Но пересоберем эту директорию, расположив ее в новой секции
+		section load_config;
+		load_config.get_raw_data().resize(1); //Мы не можем добавлять пустые секции, поэтому пусть у нее будет начальный размер данных 1
+		load_config.set_name("load_cfg"); //Имя секции
+		load_config.readable(true).writeable(true); //Доступна на чтение и запись
+		section& attached_section = image.add_section(load_config); //Добавим секцию и получим ссылку на добавленную секцию с просчитанными размерами
+
+		//Если у файла была таблица SE Handler'ов
+		if(info.get_se_handler_table_va())
+			info.add_se_handler_rva(0x7777); //Добавим новый SE Handler в таблицу (просто для теста)
+
+		//Если у файла не существовало таблицы Lock-префиксов, добавим ее
+		//(также для теста)
+		if(!info.get_lock_prefix_table_va())
+			info.add_lock_prefix_rva(0x9999);
+
+		//Пересобираем директорию Image Load Config, пересобираем таблицу Lock-префиксов, если она имелась, а также
+		//таблицу SE Handler'ов, если она есть
+		rebuild_image_config(image, info, attached_section, 1);
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/import_adder/Makefile b/irdb-lib/pebliss/trunk/samples/import_adder/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/import_adder/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcproj b/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..b7a6aebc3a98ea66a3f1f952700aabde3c591a91
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="import_adder"
+	ProjectGUID="{5303D6F1-D667-4E92-A501-8B396252156F}"
+	RootNamespace="import_adder"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcxproj b/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..2cad57a3e6b0a64c722168f196a8c867489bedff
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{EE56AFB0-A1C4-4F6D-8F90-0DB5A17C5C59}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>import_adder</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/import_adder/import_adder.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/import_adder/main.cpp b/irdb-lib/pebliss/trunk/samples/import_adder/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..6e57d66557eccf8b9aea51315b9a90ea01820466
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/import_adder/main.cpp
@@ -0,0 +1,100 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как добавить новый импорт в таблицу импорта PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: import_adder.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Получим список импортируемых библиотек и функций
+		imported_functions_list imports(get_imported_functions(image));
+
+		//Создадим новую библиотеку, из которой будем импортировать функции
+		import_library new_lib;
+		new_lib.set_name("kaimi_dx.dll"); //Пусть это будет kaimi_dx.dll
+
+		//Добавим к ней пару импортов функций
+		imported_function func;
+		func.set_name("Tralala"); //Один импорт - по имени Tralala
+		func.set_iat_va(0x1); //Запишем ненулевой абсолютный адрес в import address table
+
+		imported_function func2;
+		func2.set_ordinal(5); //Другой импорт - по ординалу 5
+		func2.set_iat_va(0x2); //Запишем ненулевой абсолютный адрес в import address table
+
+		//Мы указали некорректное содержимое (0x1 и 0x2) для ячеек, в которые будут записаны адреса импортируемых функций
+		//Это не имеет значения в общем случае, потому что эти значения всегда переписываются загрузчиком
+		//Эти адреса важны только в том случае, если exe-файл имеет привязанный импорт
+
+		//Добавим импорты
+		new_lib.add_import(func);
+		new_lib.add_import(func2);
+		imports.push_back(new_lib); //Добавим импортированную библиотеку к импортам
+
+		//Можно редактировать и существующие импорты
+
+		//Но мы просто пересоберем таблицу импортов
+		//Она будет иметь больший размер, чем до нашего редактирования,
+		//поэтому запишем ее в новую секцию, чтобы все поместилось
+		//(мы не можем расширять существующие секции, если только секция не в самом конце файла)
+		section new_imports;
+		new_imports.get_raw_data().resize(1); //Мы не можем добавлять пустые секции, поэтому пусть у нее будет начальный размер данных 1
+		new_imports.set_name("new_imp"); //Имя секции
+		new_imports.readable(true).writeable(true); //Доступна на чтение и запись
+		section& attached_section = image.add_section(new_imports); //Добавим секцию и получим ссылку на добавленную секцию с просчитанными размерами
+
+		//Структура, отвечающая за настройки пересборщика импортов
+		import_rebuilder_settings settings(true, false); //Модифицируем заголовок PE и не очищаем поле IMAGE_DIRECTORY_ENTRY_IAT
+		rebuild_imports(image, imports, attached_section, settings); //Пересобираем импорты
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/imports_reader/Makefile b/irdb-lib/pebliss/trunk/samples/imports_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/imports_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcproj b/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..a89cc345bb2b49c2530e52acd52911a00f51d7f6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="imports_reader"
+	ProjectGUID="{15AFEB1D-4EF8-4AF0-88C8-9FCA879F8AE2}"
+	RootNamespace="imports_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..36480ff1e64b8a109620cb827f605f156a6189d2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{752670B7-53AA-46CF-B3C5-D3FABBDC027D}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>imports_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/imports_reader/imports_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/imports_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/imports_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..8111fbba8f0cc82d8076e94841abf4d119f9c7f9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/imports_reader/main.cpp
@@ -0,0 +1,79 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию об импортах PE или PE+ файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: imports_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Проверим, есть ли импорты у файла
+		if(!image.has_imports())
+		{
+			std::cout << "Image has no imports" << std::endl;
+			return 0;
+		}
+
+		std::cout << "Reading PE imports..." << std::hex << std::showbase << std::endl << std::endl;
+
+		//Получаем список импортируемых библиотек с функциями
+		const imported_functions_list imports = get_imported_functions(image);
+
+		//Перечисляем импортированные библиотеки и выводим информацию о них
+		for(imported_functions_list::const_iterator it = imports.begin(); it != imports.end(); ++it)
+		{
+			const import_library& lib = *it; //Импортируемая библиотека
+			std::cout << "Library [" << lib.get_name() << "]" << std::endl //Имя
+				<< "Timestamp: " << lib.get_timestamp() << std::endl //Временная метка
+				<< "RVA to IAT: " << lib.get_rva_to_iat() << std::endl //Относительный адрес к import address table
+				<< "========" << std::endl;
+
+			//Перечисляем импортированные функции для библиотеки
+			const import_library::imported_list& functions = lib.get_imported_functions();
+			for(import_library::imported_list::const_iterator func_it = functions.begin(); func_it != functions.end(); ++func_it)
+			{
+				const imported_function& func = *func_it; //Импортированная функция
+				std::cout << "[+] ";
+				if(func.has_name()) //Если функция имеет имя - выведем его
+					std::cout << func.get_name();
+				else
+					std::cout << "#" << func.get_ordinal(); //Иначе она импортирована по ординалу
+
+				//Хинт
+				std::cout << " hint: " << func.get_hint() << std::endl;
+			}
+
+			std::cout << std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/lib.h b/irdb-lib/pebliss/trunk/samples/lib.h
new file mode 100644
index 0000000000000000000000000000000000000000..27d33526d5ecbf057866415831032aede4ce6cb9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/lib.h
@@ -0,0 +1,14 @@
+#pragma once
+#ifndef _M_X64
+#ifdef _DEBUG
+#pragma comment(lib, "../../Debug/pe_bliss.lib")
+#else
+#pragma comment(lib, "../../Release/pe_bliss.lib")
+#endif
+#else
+#ifdef _DEBUG
+#pragma comment(lib, "../../x64/Debug/pe_bliss.lib")
+#else
+#pragma comment(lib, "../../x64/Release/pe_bliss.lib")
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/samples/pe_config_reader/Makefile b/irdb-lib/pebliss/trunk/samples/pe_config_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_config_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/pe_config_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/pe_config_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e190aa2a6ba1effd789d4ec80f6b76eb6b2af6f1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_config_reader/main.cpp
@@ -0,0 +1,67 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию о Image Config (конфигурация исполняемого файла) PE или PE+
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: pe_config_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		std::cout << "Reading PE image config info..." << std::hex << std::showbase << std::endl << std::endl;
+		
+		//Получаем конфигурацию
+		const image_config_info info(get_image_config(image));
+
+		//Выводим данные конфигурации
+		//Подробнее о полях - в MSDN
+		std::cout << "Critical section default timeout: " << info.get_critical_section_default_timeout() << std::endl
+			<< "Decommit free block threshold: " << info.get_decommit_free_block_threshold() << std::endl
+			<< "Decommit total free threshold: " << info.get_decommit_total_free_threshold() << std::endl
+			<< "Global flags clear: " << info.get_global_flags_clear() << std::endl
+			<< "Global flags set: " << info.get_global_flags_set() << std::endl
+			<< "VA of lock table prefix: " << info.get_lock_prefix_table_va() << std::endl
+			<< "Max allocation size: " << info.get_max_allocation_size() << std::endl
+			<< "Process affinity mask: " << info.get_process_affinity_mask() << std::endl
+			<< "Process heap flags: " << info.get_process_heap_flags() << std::endl
+			<< "Security cookie VA: " << info.get_security_cookie_va() << std::endl
+			<< "CSDVersion: " << info.get_service_pack_version() << std::endl
+			<< "Timestamp: " << info.get_time_stamp() << std::endl
+			<< "Virtual memory threshold: " << info.get_virtual_memory_threshold() << std::endl
+			<< std::endl;
+
+		//Выведем адреса SE-хендлеров
+		const image_config_info::se_handler_list& se_handlers = info.get_se_handler_rvas();
+		for(image_config_info::se_handler_list::const_iterator it = se_handlers.begin(); it != se_handlers.end(); ++it)
+			std::cout << "SE Handler: " << (*it) << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcproj b/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..ea301cc36615b76ba8fe20d7ad0d47a5343d2c88
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="pe_config_reader"
+	ProjectGUID="{1F7B06CA-5529-4A3D-89CE-15161D4A01D9}"
+	RootNamespace="pe_config_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..815c460db6fe82c24f1c0f24ee582b1aa07e0a63
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{4F642892-D07F-4A96-82E4-36E2966D222D}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>pe_config_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_config_reader/pe_config_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_realigner/Makefile b/irdb-lib/pebliss/trunk/samples/pe_realigner/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_realigner/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/pe_realigner/main.cpp b/irdb-lib/pebliss/trunk/samples/pe_realigner/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..849d07ce069257f2e88e9cb7d3cd814a61b696d9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_realigner/main.cpp
@@ -0,0 +1,84 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как изменить файловое выравнивание PE-файлов
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: pe_realigner.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Выведем темущий file alignment
+		std::cout << "File alignment: " << image.get_file_alignment() << std::endl;
+		
+		//Предложим выбрать новое выравнивание
+		unsigned int new_alignment_index = static_cast<unsigned int>(-1);
+
+		while(new_alignment_index > 3)
+		{
+			if(std::cin.fail())
+			{
+				//На случай, если пользователь ввел что-то некорректное
+				std::cin.clear();
+				std::cin.ignore(static_cast<std::streamsize>(-1), '\n');
+			}
+
+			std::cout << "Choose new file alignment" << std::endl;
+			std::cout << "(0 = 512, 1 = 1024, 2 = 2048, 3 = 4096): ";
+			std::cin >> new_alignment_index;
+		}
+		
+		unsigned int available_aligns[] = {512, 1024, 2048, 4096};
+
+		//Изменим выравнивание на то, которое указал пользователь
+		image.realign_file(available_aligns[new_alignment_index]);
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcproj b/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..9b9a452f4b74edaa99d22b854ba37ae182b2a13a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="pe_realigner"
+	ProjectGUID="{36EB9E03-E155-4487-AB1B-0B1B862B0155}"
+	RootNamespace="pe_realigner"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcxproj b/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..0668df485234300905acc268d201f91415ba4221
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{F40CE9C6-5E3F-445A-8EA4-ED819E608024}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>pe_realigner</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_realigner/pe_realigner.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_rebaser/Makefile b/irdb-lib/pebliss/trunk/samples/pe_rebaser/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_rebaser/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/pe_rebaser/main.cpp b/irdb-lib/pebliss/trunk/samples/pe_rebaser/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..6a79856505461720817b857f3eab0c2690b6ac99
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_rebaser/main.cpp
@@ -0,0 +1,73 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как изменить базовый адрес загрузки PE-файла при условии наличия релокаций
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: pe_rebaser.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Проверим, есть ли релокации у образа
+		if(!image.has_reloc())
+		{
+			std::cout << "Image has no relocations, rebase is not possible" << std::endl;
+			return 0;
+		}
+
+		//Получим значение базового адреса загрузки образа (64-бита, универсально для PE и PE+)
+		uint64_t base = image.get_image_base_64();
+		base += 0x100000; //Изменим базовый адрес загрузки
+		
+		//Произведем пересчет необходимых адресов
+		rebase_image(image, get_relocations(image), base);
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcproj b/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..04dfbb53d324d1ee38112a63c8240296326b90f1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="pe_rebaser"
+	ProjectGUID="{0F52C42C-EEDA-4031-B0A0-F6CD53C81465}"
+	RootNamespace="pe_rebaser"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcxproj b/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..a019cde1f0e65e41691fc2ba50a6747a6e965a9e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{46FD39E7-B16C-4F73-B2F0-F1B570464C6E}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>pe_rebaser</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_rebaser/pe_rebaser.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_sections_reader/Makefile b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/pe_sections_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1d5c9ecb91b7d5609b1ba1c17e652c558df7a13d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/main.cpp
@@ -0,0 +1,56 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию о секциях PE или PE+ файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: pe_sections_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Получаем список секций
+		std::cout << "Reading PE sections..." << std::hex << std::showbase << std::endl << std::endl;
+		const section_list sections(image.get_image_sections());
+
+		//Перечисляем секции и выводим информацию о них
+		for(section_list::const_iterator it = sections.begin(); it != sections.end(); ++it)
+		{
+			const section& s = *it; //Секция
+			std::cout << "Section [" << s.get_name() << "]" << std::endl //Имя секции
+				<< "Characteristics: " << s.get_characteristics() << std::endl //Характеристики
+				<< "Size of raw data: " << s.get_size_of_raw_data() << std::endl //Размер данных в файле
+				<< "Virtual address: " << s.get_virtual_address() << std::endl //Виртуальный адрес
+				<< "Virtual size: " << s.get_virtual_size() << std::endl //Виртуальный размер
+				<< std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcproj b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..5d9eb5c447d110caba4f0d7928897cc466d4b838
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="pe_sections_reader"
+	ProjectGUID="{0A06D231-FC40-4EC9-B0FC-F0D08270384E}"
+	RootNamespace="pe_sections_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..119584e311d17139c1b56040cb00fb7ee520ba91
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcxproj
@@ -0,0 +1,162 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{F154B72B-22DD-493A-B5D5-CDCD8914DA28}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>pe_sections_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <AdditionalDependencies>%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <AdditionalDependencies>%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+      <AdditionalDependencies>%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+      <AdditionalDependencies>%(AdditionalDependencies)</AdditionalDependencies>
+    </Link>
+  </ItemDefinitionGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_sections_reader/pe_sections_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_stripper/Makefile b/irdb-lib/pebliss/trunk/samples/pe_stripper/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_stripper/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/pe_stripper/main.cpp b/irdb-lib/pebliss/trunk/samples/pe_stripper/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..ecc147ea00b6a072dce574de35d43fca2518106d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_stripper/main.cpp
@@ -0,0 +1,69 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как вырезать ненужные данные из PE-файла и пересобрать его
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: pe_stripper.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Удалим DOS stub и rich overlay
+		image.strip_stub_overlay();
+
+		//Удалим ненужные DATA_DIRECTORY (нулевые)
+		//Очень малое количество линкеров умеют это делать
+		image.strip_data_directories(0);
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл с опцией сжатия DOS-header
+		//Уменьшения размера это не дает, но упаковывает NT-заголовки в DOS-заголовок
+		//При пересборке автоматически убираются ненужные нулевые байты в самом конце образа,
+		//в результате чего размер образа становится немного меньше
+		rebuild_pe(image, new_pe_file, true);
+		
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcproj b/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..a649e2e22ddba9b0098ab7818c78298cc148339d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="pe_stripper"
+	ProjectGUID="{9E09B1EB-D3F3-4C38-B87F-AE642F509D04}"
+	RootNamespace="pe_stripper"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcxproj b/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..dab516938a65d8cc43421100dcc03f7ce83ad15f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{B32991F6-CD2C-48FE-A2AE-BDE8A4AC847D}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>pe_stripper</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/pe_stripper/pe_stripper.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/relocation_adder/Makefile b/irdb-lib/pebliss/trunk/samples/relocation_adder/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocation_adder/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/relocation_adder/main.cpp b/irdb-lib/pebliss/trunk/samples/relocation_adder/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..b5f6965ea1688763dada1ca1f0e14c6fcc76cb8b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocation_adder/main.cpp
@@ -0,0 +1,87 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как добавить новую релокацию в таблицы релокаций PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: relocation_adder.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Перечислим и получим все записи из таблиц релокаций в PE-файле, кроме абсолютных
+		//Можно было бы включить в список и абсолютные записи (ABSOLUTE), передав в вызов true
+		//Эти записи не нужны при пересборке релокаций, они используются для выравнивания
+		//и будут добавлены автоматически пересборщиком
+		relocation_table_list tables(get_relocations(image));
+		
+		//Создаем новую таблицу релокаций
+		relocation_table new_table;
+		new_table.set_rva(0x5678); //Относительный адрес релокаций в таблице - он некорректен, для примера, поэтому получившийся PE скорее всего не загрузится
+		//Добавим в таблицу новую релокацию
+		new_table.add_relocation(relocation_entry(10, 3)); //Тип 3 - HIGHLOW-релокация, RRVA = 10, т.е. RVA = 0x5678 + 10
+		//Добавляем таблицу
+		tables.push_back(new_table);
+
+		//Можно редактировать и существующие релокации, но делать этого не стоит, так как файл не загрузится, если что-то в них поменять
+		//Если их удалить у EXE-файла полностью, то все будет нормально, у DLL этого делать не стоит
+		//Мы просто пересоберем релокации
+		//Они будет иметь больший размер, чем до нашего редактирования,
+		//поэтому запишем их в новую секцию, чтобы все поместилось
+		//(мы не можем расширять существующие секции, если только секция не в самом конце файла)
+		section new_relocs;
+		new_relocs.get_raw_data().resize(1); //Мы не можем добавлять пустые секции, поэтому пусть у нее будет начальный размер данных 1
+		new_relocs.set_name("new_rel"); //Имя секции
+		new_relocs.readable(true); //Доступна на чтение
+		section& attached_section = image.add_section(new_relocs); //Добавим секцию и получим ссылку на добавленную секцию с просчитанными размерами
+
+		rebuild_relocations(image, tables, attached_section); //Пересобираем экспорты, расположив их с начала новой секции и записав новые данные таблиц релокаций в PE-заголовок
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcproj b/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..e7d84353096c58082ed579784c3d1d5f24cfd151
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="relocation_adder"
+	ProjectGUID="{9E7C038E-470E-4DF8-A887-3E1B8A02B78C}"
+	RootNamespace="relocation_adder"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcxproj b/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..df1f34f6bc61f9a31a146bfaf5f24051741c45c1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{7375047B-90D7-4564-BA84-7E5C638C7CCE}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>relocation_adder</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocation_adder/relocation_adder.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/relocations_reader/Makefile b/irdb-lib/pebliss/trunk/samples/relocations_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocations_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/relocations_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/relocations_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..989f5ff8483eaba0bb4cc85c5d72a1ac8199ec6b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocations_reader/main.cpp
@@ -0,0 +1,70 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию о релокациях PE или PE+ файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: relocations_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Проверим, есть ли релокации у файла
+		if(!image.has_reloc())
+		{
+			std::cout << "Image has no relocations" << std::endl;
+			return 0;
+		}
+
+		std::cout << "Reading PE relocations..." << std::hex << std::showbase << std::endl << std::endl;
+
+		//Получаем список таблиц релокаций
+		const relocation_table_list tables(get_relocations(image));
+
+		//Перечисляем таблицы релокаций и выводим информацию о них
+		for(relocation_table_list::const_iterator it = tables.begin(); it != tables.end(); ++it)
+		{
+			const relocation_table& table = *it; //Таблица релокаций
+			std::cout << "RVA [" << table.get_rva() << "]" << std::endl //Относительный адрес
+				<< "=========="
+				<< std::endl;
+
+			//Перечислим все релокации
+			const relocation_table::relocation_list& relocs = table.get_relocations();
+			for(relocation_table::relocation_list::const_iterator reloc_it = relocs.begin(); reloc_it != relocs.end(); ++reloc_it)
+			{
+				std::cout << "[+] " << (*reloc_it).get_item() << std::endl;
+			}
+
+			std::cout << std::endl;
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcproj b/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..5a18e10eb94cf4280d3adb74fe5e3f6e79ae72be
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="relocations_reader"
+	ProjectGUID="{3EDCB092-C785-41EB-8A83-C5B37A2FF310}"
+	RootNamespace="relocations_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..5f17bca9921d9aa81f5d69ea6aa1fb14fc1fb14a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{A188C743-EA65-4D18-8964-18EAE61ACAC2}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>relocations_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/relocations_reader/relocations_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/Makefile b/irdb-lib/pebliss/trunk/samples/resource_editor/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_editor/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/main.cpp b/irdb-lib/pebliss/trunk/samples/resource_editor/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..935fc712bd5a87af14d02b574c73f5c5ed7a15ee
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_editor/main.cpp
@@ -0,0 +1,175 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#ifdef PE_BLISS_WINDOWS
+#include "resource.h"
+#include "lib.h"
+#else
+#define IDR_CUSTOM1 100
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как редактировать ресурсы PE-файла
+//Для начала рекомендуется ознакомиться с примером resource_viewer
+//Обратите внимание, что пример корректно отработает и в x86, и в x64 варианте
+int main(int argc, char* argv[])
+{
+	std::string pe_filename;
+
+#ifdef PE_BLISS_WINDOWS
+	//Открываем файл (сами себя)
+	pe_filename = argv[0];
+#else
+	std::cout << "This sample needs itself to be compiled on Windows"
+		<< std::endl << "Enter its filename: ";
+
+	std::cin >> pe_filename;
+#endif
+	
+	std::ifstream pe_file(pe_filename.c_str(), std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << pe_filename << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Суть примера будет состоять в следующем:
+		//В сам пример вкомпиливается иконка в директорию с именем CUSTOM
+		//Иконка состоит из трех картинок разных разрешений
+		//Наша задача - считать иконку из директории CUSTOM и установить ее как главную иконку exe-файла
+		//Далее - удалить директорию CUSTOM
+		//Наконец, добавить какую-нибудь информацию о версии к файлу
+
+		//Проверим, есть ли ресурсы у файла
+		if(!image.has_resources())
+		{
+			std::cout << "Image has no resources" << std::endl;
+			return 0;
+		}
+
+		//Получаем корневую директорию ресурсов
+		std::cout << "Reading PE resources..." << std::hex << std::showbase << std::endl << std::endl;
+		resource_directory root(get_resources(image));
+
+		//Для облегчения работы с директориями и записями ресурсов созданы вспомогательные классы
+		//Этот класс позволяет извлекать из PE-файлов любые ресурсы и перезаписывать их
+		//и предоставляет высокоуровневые функции для извечения иконок, курсоров, картинкок, строковых таблиц
+		//и таблиц сообщений, а также информации о версии
+		//и редактирования иконок, курсоров, картинок и информации о версии
+		pe_resource_manager res(root);
+
+		//Для начала убедимся, что директория CUSTOM есть
+		if(!res.resource_exists(L"CUSTOM"))
+		{
+			std::cout << "\"CUSTOM\" resource directory does not exist" << std::endl;
+			return -1;
+		}
+
+		//Получим нашу иконку из этой директории: мы знаем, что ее ID=100 и она одна в директории имен, поэтому делаем так
+		//Получаем ее по нулевому индексу (можно было получить по языку, но это незачем, т.к. она единственная)
+		const resource_data_info data = res.get_resource_data_by_id(L"CUSTOM", IDR_CUSTOM1);
+
+		//Необходимо теперь добавить ее как главную иконку
+		//Иконка приложения - это иконка из той группы иконок, которая следует самой первой в списке групп иконок
+		//Помните, что сначала идут именованные ресурсы, а потом ресурсы с идентификаторами, и всё сортируется
+		//Создадим группу иконок с именем MAIN_ICON
+		resource_cursor_icon_writer(res).add_icon(data.get_data(), //Данные файла иконки
+			L"MAIN_ICON", //Имя группы иконок (помните, у нас три картинки внутри иконки, они будут находиться в этой группе)
+			0, //Язык - нам неважен
+			resource_cursor_icon_writer::icon_place_after_max_icon_id, //Вариант расположения иконок в существующей группе - нам он неважен, так как мы создаем новую группу
+			data.get_codepage(), //Сохраним исходную Codepage
+			0 //Timestamp - неважен
+			);
+		
+		//Теперь удалим уже ненужный ресурс CUSTOM
+		res.remove_resource(L"CUSTOM");
+		
+		//Теперь создадим информацию о версии
+		file_version_info file_info; //Базовая информация о файле
+		file_info.set_special_build(true); //Это будет специальный билд
+		file_info.set_file_os(file_version_info::file_os_nt_win32); //Система, на которой работает файл
+		file_info.set_file_version_ms(0x00010002); //Версия файла будет 1.2.3.4
+		file_info.set_file_version_ls(0x00030004);
+
+		//Теперь создадим строки с информацией и трансляции (переводы)
+		lang_string_values_map strings;
+		translation_values_map translations;
+
+		//Для работы со строками и трансляциями есть вспомогательный класс
+		version_info_editor version(strings, translations);
+		//Добавим трансляцию - default process language, UNICODE
+		//Можно указать и конкретный язык и кодировку
+		version.add_translation(version_info_editor::default_language_translation);
+		//Строки будут устанавливаться для дефолтной кодировки (default_language_translation)
+		//Если такой нет, то для первой найденной
+		//Если вообще нет ни одной трансляции, то будет добавлена дефолтная (default_language_translation)
+		//Таким образом, предыдущий вызов add_translation можно было бы опустить
+		//И еще: необязательно устанавливать все доступные строки, как сделано ниже
+		version.set_company_name(L"Kaimi.ru DX"); //Имя компании-производителя
+		version.set_file_description(L"Generated file version info"); //Описание файла
+		version.set_internal_name(L"Tralala.exe"); //Внутреннее имя файла
+		version.set_legal_copyright(L"(C) DX Portable Executable Library"); //Копирайт
+		version.set_original_filename(L"resource_editor.exe"); //Оригинальное имя файла
+		version.set_product_name(L"PE Resource Editor Example"); //Имя продукта
+		version.set_product_version(L"x.y.z"); //Версия продукта
+
+		//Можно также добавить свою собственную строку: она будет храниться в информации о версии,
+		//но Windows Explorer вряд ли ее отобразит в свойствах файла
+		version.set_property(L"MyLittleProperty", L"Secret Value");
+
+		//Установим информацию о версии
+		resource_version_info_writer(res).set_version_info(file_info, strings, translations, 1033); //1033 - русский язык
+		
+		//Осталось переименовать старую секцию ресурсов
+		//Она называется .rsrc
+		//Переименование необходимо для того, чтобы Windows Explorer смог считать из новой секции иконку
+		image.section_from_directory(pe_win::image_directory_entry_resource).set_name("oldres");
+
+		//Пересоберем ресурсы
+		//Они будет иметь больший размер, чем до нашего редактирования,
+		//поэтому запишем их в новую секцию, чтобы все поместилось
+		//(мы не можем расширять существующие секции, если только секция не в самом конце файла)
+		section new_resources;
+		new_resources.get_raw_data().resize(1); //Мы не можем добавлять пустые секции, поэтому пусть у нее будет начальный размер данных 1
+		new_resources.set_name(".rsrc"); //Имя секции
+		new_resources.readable(true); //Доступна на чтение
+		section& attached_section = image.add_section(new_resources); //Добавим секцию и получим ссылку на добавленную секцию с просчитанными размерами
+		
+		//Теперь пересоберем ресурсы, расположив их в самом начале новой секции и поправив PE-заголовок, записав туда новые параметры директории ресурсы
+		rebuild_resources(image, root, attached_section);
+		
+		//Создаем новый PE-файл
+		std::string base_file_name(pe_filename);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/resource.h b/irdb-lib/pebliss/trunk/samples/resource_editor/resource.h
new file mode 100644
index 0000000000000000000000000000000000000000..ce9e9c169c920c311e809b3d6ff0b25344eee022
Binary files /dev/null and b/irdb-lib/pebliss/trunk/samples/resource_editor/resource.h differ
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/resource.rc b/irdb-lib/pebliss/trunk/samples/resource_editor/resource.rc
new file mode 100644
index 0000000000000000000000000000000000000000..234fa23e3975d323df1492e032039cde9dabc300
Binary files /dev/null and b/irdb-lib/pebliss/trunk/samples/resource_editor/resource.rc differ
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcproj b/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..260f28dcf15ea543a9c6ff05bd9e7ddc74c1e4c2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcproj
@@ -0,0 +1,363 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="resource_editor"
+	ProjectGUID="{B0D287DB-451D-4005-9CE3-185D7602F0B7}"
+	RootNamespace="resource_editor"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath=".\resource.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+			<File
+				RelativePath=".\resource.rc"
+				>
+			</File>
+			<File
+				RelativePath=".\wxwin.ico"
+				>
+			</File>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcxproj b/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..0812f7422ca1d4b6ac431d98659a39045b5ef845
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcxproj
@@ -0,0 +1,165 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{B88455A6-C93A-4F17-93A5-FC84B70F9CFE}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>resource_editor</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="resource.h" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ResourceCompile Include="resource.rc" />
+  </ItemGroup>
+  <ItemGroup>
+    <None Include="wxwin.ico" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..97def5d8b734ed771f93724b34503f9d22aaeba9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_editor/resource_editor.vcxproj.filters
@@ -0,0 +1,40 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="resource.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ResourceCompile Include="resource.rc">
+      <Filter>Resource Files</Filter>
+    </ResourceCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <None Include="wxwin.ico">
+      <Filter>Resource Files</Filter>
+    </None>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/resource_editor/wxwin.ico b/irdb-lib/pebliss/trunk/samples/resource_editor/wxwin.ico
new file mode 100644
index 0000000000000000000000000000000000000000..719de36e163e34eaa4a03665873045b831757c5a
Binary files /dev/null and b/irdb-lib/pebliss/trunk/samples/resource_editor/wxwin.ico differ
diff --git a/irdb-lib/pebliss/trunk/samples/resource_viewer/Makefile b/irdb-lib/pebliss/trunk/samples/resource_viewer/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_viewer/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/resource_viewer/main.cpp b/irdb-lib/pebliss/trunk/samples/resource_viewer/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..653b143864540acfacfb3390c26f0c05ccef3811
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_viewer/main.cpp
@@ -0,0 +1,226 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как читать ресурсы PE-файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: resource_viewer.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Проверим, есть ли ресурсы у файла
+		if(!image.has_resources())
+		{
+			std::cout << "Image has no resources" << std::endl;
+			return 0;
+		}
+
+		//Получаем корневую директорию ресурсов
+		std::cout << "Reading PE resources..." << std::hex << std::showbase << std::endl << std::endl;
+		const resource_directory root(get_resources(image));
+
+		//Для облегчения работы с директориями и записями ресурсов созданы вспомогательные классы
+		//Этот класс позволяет извлекать из PE-файлов любые ресурсы
+		//и предоставляет высокоуровневые функции для извечения иконок, курсоров, картинкок, строковых таблиц
+		//и таблиц сообщений, а также информации о версии
+		pe_resource_viewer res(root);
+
+		//Выведем типы ресурсов, которые присутствуют в PE-файле
+		pe_resource_viewer::resource_type_list res_types(res.list_resource_types());
+		for(pe_resource_viewer::resource_type_list::const_iterator it = res_types.begin(); it != res_types.end(); ++it)
+			std::cout << "Present resource type: " << (*it) << std::endl;
+
+		std::cout << std::endl;
+
+		//Выведем иофнрмацию о версии, если она существует
+		if(res.resource_exists(pe_resource_viewer::resource_version))
+		{
+			lang_string_values_map strings;
+			translation_values_map translations;
+			//Получаем список строк, переводов и базовую информацию о файле
+			file_version_info file_info(resource_version_info_reader(res).get_version_info(strings, translations));
+
+			//Выводить информацию будем в юникодный поток
+			std::wstringstream version_info;
+			//Выведем некоторую базовую информацию
+			version_info << L"Version info: " << std::endl;
+			version_info << L"File version: " << file_info.get_file_version_string<wchar_t>() << std::endl; //Строка версии файла
+			version_info << L"Debug build: " << (file_info.is_debug() ? L"YES" : L"NO") << std::endl; //Отладочный ли билд
+			version_info << std::endl;
+
+			//Выведем строки для разных трансляций:
+			for(lang_string_values_map::const_iterator it = strings.begin(); it != strings.end(); ++it)
+			{
+				version_info << L"Translation ID: " << (*it).first << std::endl;
+
+				//Перечислим записи в таблице строк для текущей трансляции (перевода)
+				const string_values_map& string_table = (*it).second;
+				for(string_values_map::const_iterator str_it = string_table.begin(); str_it != string_table.end(); ++str_it)
+					version_info << (*str_it).first << L": " << (*str_it).second << std::endl;
+
+				version_info << std::endl;
+			}
+			
+			//Выведем доступные переводы (трансляции):
+			for(translation_values_map::const_iterator it = translations.begin(); it != translations.end(); ++it)
+				version_info << L"Translation: language: " << (*it).first << ", codepage: " << (*it).second << std::endl;
+
+			{
+				//Создаем файл, в который запишем информацию о версии
+				std::ofstream version_info_file("version_info.txt", std::ios::out | std::ios::trunc | std::ios::binary);
+				if(!version_info_file)
+				{
+					std::cout << "Cannot create file version_info.txt" << std::endl;
+					return -1;
+				}
+
+				std::wstring version_info_string(version_info.str());
+				//Запишем буфер, чтобы не париться с локалями и записью юникода в файл
+				version_info_file.write(reinterpret_cast<const char*>(version_info_string.data()), version_info_string.length() * sizeof(wchar_t));
+
+				std::cout << "version_info.txt created" << std::endl << std::endl;
+			}
+
+			//Для облегчения чтения информации о версии есть специальный класс
+			version_info_viewer version_viewer(strings, translations);
+			std::wcout << L"Original filename: " << version_viewer.get_original_filename() << std::endl << std::endl;
+		}
+
+		{
+			//Найдем, есть ли у приложения иконка
+			//Для этого сначала узнаем все имена и идентификаторы групп иконок
+			//Все ресурсы в целом организованы в таком виде (дерево):
+			//тип ресурса
+			//--> имя ресурса
+			//----> язык рерурса
+			//------> ресурс
+			//----> язык ресурса
+			//------> ресурс
+			//----> ...
+			//--> имя ресурса
+			//--> ...
+			//--> id ресурса
+			//----> язык рерурса
+			//------> ресурс
+			//----> язык ресурса
+			//------> ресурс
+			//----> ...
+			//--> id ресурса
+			//--> ...
+			//тип ресурса
+			//...
+			pe_resource_viewer::resource_id_list icon_id_list(res.list_resource_ids(pe_resource_viewer::resource_icon_group));
+			pe_resource_viewer::resource_name_list icon_name_list(res.list_resource_names(pe_resource_viewer::resource_icon_group));
+			std::string main_icon; //Данные иконки приложения
+			//Сначала всегда располагаются именованные ресурсы, поэтому проверим, есть ли они
+			if(!icon_name_list.empty())
+			{
+				//Получим самую первую иконку для самого первого языка (по индексу 0)
+				//Если надо было бы перечислить языки для заданной иконки, можно было вызвать list_resource_languages
+				//Если надо было бы получить иконку для конкретного языка, можно было вызвать get_icon_by_name (перегрузка с указанием языка)
+				main_icon = resource_cursor_icon_reader(res).get_icon_by_name(icon_name_list[0]);
+			}
+			else if(!icon_id_list.empty()) //Если нет именованных групп иконок, но есть группы с ID
+			{
+				//Получим самую первую иконку для самого первого языка (по индексу 0)
+				//Если надо было бы перечислить языки для заданной иконки, можно было вызвать list_resource_languages
+				//Если надо было бы получить иконку для конкретного языка, можно было вызвать get_icon_by_id_lang
+				main_icon = resource_cursor_icon_reader(res).get_icon_by_id(icon_id_list[0]);
+			}
+
+			//Если есть иконка...
+			if(!main_icon.empty())
+			{
+				//Сохраним полученную иконку в файл
+				std::ofstream app_icon("main_icon.ico", std::ios::out | std::ios::trunc | std::ios::binary);
+				if(!app_icon)
+				{
+					std::cout << "Cannot create file main_icon.ico" << std::endl;
+					return -1;
+				}
+
+				app_icon.write(main_icon.data(), main_icon.length());
+
+				std::cout << "main_icon.ico created" << std::endl;
+			}
+		}
+
+		{
+			//Сдампим строковые таблицы
+			//Перечислим идентификаторы существующих строковых таблиц
+			pe_resource_viewer::resource_id_list strings_id_list(res.list_resource_ids(pe_resource_viewer::resource_string));
+
+			//Дампить будем в юникодный поток
+			std::wstringstream string_data;
+
+			if(!strings_id_list.empty()) //Если у нас есть именованные строковые таблицы, сдампим их
+			{
+				//Все имена строковых таблиц
+				for(pe_resource_viewer::resource_id_list::const_iterator it = strings_id_list.begin(); it != strings_id_list.end(); ++it)
+				{
+					string_data << L"String table [" << (*it) << L"]" << std::endl;
+
+					//Перечислим языки таблицы
+					pe_resource_viewer::resource_language_list langs(res.list_resource_languages(pe_resource_viewer::resource_string, *it));
+					//Для каждого языка получим таблицу строк
+					for(pe_resource_viewer::resource_language_list::const_iterator lang_it = langs.begin(); lang_it != langs.end(); ++lang_it)
+					{
+						string_data << L" -> Language = " << *lang_it << std::endl; //Запишем язык
+						//Таблица строк
+						resource_string_list strings(resource_string_table_reader(res).get_string_table_by_id_lang(*lang_it, *it));
+
+						//Наконец, запишем все строки в поток
+						for(resource_string_list::const_iterator str_it = strings.begin(); str_it != strings.end(); ++str_it)
+							string_data << L" --> #" << (*str_it).first << L": " << (*str_it).second << std::endl; //ID строки: ее значение
+					}
+
+					string_data << std::endl;
+				}
+				
+				//Запишем полученные строки в файл
+				std::ofstream strings_file("strings.txt", std::ios::out | std::ios::trunc | std::ios::binary);
+				if(!strings_file)
+				{
+					std::cout << "Cannot create file strings.txt" << std::endl;
+					return -1;
+				}
+
+				std::wstring strings_str(string_data.str());
+				//Запишем буфер, чтобы не париться с локалями и записью юникода в файл
+				strings_file.write(reinterpret_cast<const char*>(strings_str.data()), strings_str.length() * sizeof(wchar_t));
+
+				std::cout << "strings.txt created" << std::endl;
+			}
+		}
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcproj b/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..8482c29f6bd78cc83113e87ead0b1ff6cad61770
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="resource_viewer"
+	ProjectGUID="{D10B61A9-09FD-4E87-8C66-BE07AE5CC8E9}"
+	RootNamespace="resource_viewer"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcxproj b/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..697c1c1f23dc91f73a11d6b2b69682ff35023ba6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{BC2D8697-73C1-46B9-AC1C-7777D1A71609}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>resource_viewer</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/resource_viewer/resource_viewer.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/Makefile b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..fa7bac5ca451ca68a2f55083fc5929c892fb14c1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/main.cpp
@@ -0,0 +1,57 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как получить информацию о стабе PE-файла и rich overlay, который добавляет при компиляции MS Visual Studio
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: rich_overlay_stub_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Выведем длину DOS stub'а
+		std::cout << "Image stub length: " << image.get_stub_overlay().length() << std::endl << std::endl;
+
+		//Перечисляем все RICH-записи
+		rich_data_list data = get_rich_data(image);
+		for(rich_data_list::const_iterator it = data.begin(); it != data.end(); ++it)
+		{
+			//Выводим информацию о записи
+			std::cout << "Number: " << (*it).get_number() << std::endl
+				<< "Times: " << (*it).get_times() << std::endl
+				<< "Version: " << (*it).get_version() << std::endl
+				<< std::endl;
+		}
+
+		//Отобразим информацию о том, есть ли у файла оверлей в конце (у некоторых инсталляторов, например, есть)
+		std::cout << "Has overlay in the end: " << (image.has_overlay() ? "YES" : "NO") << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcproj b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..ed7648d9106e04d1e8eb244260969f1bb83f24d6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="rich_overlay_stub_reader"
+	ProjectGUID="{33FF435B-A3CF-441E-964E-A7DA8735E7B1}"
+	RootNamespace="rich_overlay_stub_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..16b5b014852a8850a021d9baed0f0a4db160f219
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{3FDDF315-4CD6-4A21-91CE-F5AFF5BB9667}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>rich_overlay_stub_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/rich_overlay_stub_reader/rich_overlay_stub_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/sample.mak b/irdb-lib/pebliss/trunk/samples/sample.mak
new file mode 100644
index 0000000000000000000000000000000000000000..688875a862800bc431e876301dc3d4461c40ffb9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/sample.mak
@@ -0,0 +1,24 @@
+PWD=$(shell pwd)
+OUTDIR = ../out/
+LIBPATH = ../../lib/libpebliss.a
+NAME=$(shell basename $(PWD))
+CXXFLAGS =  -Wall -I../../pe_lib
+
+ifdef PE_DEBUG
+CXXFLAGS  += -g -O0
+endif
+
+all: $(OUTDIR)$(NAME)
+
+clean:
+	rm -f $(NAME) *.o
+	rm -f $(OUTDIR)$(NAME)
+
+$(NAME): main.o
+	$(CXX) -Wall $^ -lpebliss -L../../lib -o $(NAME) -liconv
+
+main.o: $(LIBPATH)
+
+$(OUTDIR)$(NAME): $(NAME)
+	cp -d $(NAME) $(OUTDIR)
+
diff --git a/irdb-lib/pebliss/trunk/samples/section_adder/Makefile b/irdb-lib/pebliss/trunk/samples/section_adder/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/section_adder/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/section_adder/main.cpp b/irdb-lib/pebliss/trunk/samples/section_adder/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..227c4fdbdaf7eb3fe6915b0d70363de0d854ccbf
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/section_adder/main.cpp
@@ -0,0 +1,74 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как добавить секцию в PE-файл и записать в нее какие-нибудь данные
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: section_adder.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+		
+		//Секцию можно добавить только после всех существующих, чтобы PE-файл не испортился
+		//Создаем новую секцию
+		section new_section;
+		new_section.readable(true).writeable(true); //Делаем секцию доступной для чтения и записи
+		new_section.set_name("kaimi.ru"); //Ставим имя секции - максимум 8 символов
+		new_section.set_raw_data("Tralala"); //Устанавливаем данные секции
+
+		//Добавляем секцию. Все адреса пересчитаются автоматически
+		//Вызов вернет ссылку на уже добавленную секцию с пересчитанными адресами
+		//Совсем пустую секцию к образу добавить нельзя, у нее должен быть ненулевой размер данных или виртуальный размер
+		section& added_section = image.add_section(new_section);
+
+		//Если нужно изменить виртуальный размер секции, то делается это так:
+		image.set_section_virtual_size(added_section, 0x1000);
+		
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcproj b/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..2011bee8055eccf1baddeca083b8caedd36aa964
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="section_adder"
+	ProjectGUID="{C3B58F69-FA5D-4E9E-8E21-F6C5EBAC22ED}"
+	RootNamespace="section_adder"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcxproj b/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..85a2e4ddaae2ea8b861624566925c042d4d7f9bf
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{93ABC577-1018-48C2-95C6-39B0B26DD3B0}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>section_adder</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/section_adder/section_adder.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/sections_and_addresses/Makefile b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/sections_and_addresses/main.cpp b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a6d12b8e895e7c3cddf1eb66fa0db7624a2fd7b6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/main.cpp
@@ -0,0 +1,50 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как работать с секциями в PE-файле
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: sections_and_addresses.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Выведем имя секции, в которой находится точка входа PE-файла
+		//В хитрых PE-файлах точка входа может находиться в заголовке, тогда section_from_rva бросит исключение
+		std::cout << "EP section name: " << image.section_from_rva(image.get_ep()).get_name() << std::endl;
+		//Длина "сырых" (raw) данных секции
+		std::cout << "EP section data length: " << image.section_data_length_from_rva(image.get_ep()) << std::endl;
+
+		//Если у PE-файла есть импорты, выведем имя секции, в которой они находятся
+		if(image.has_imports())
+			std::cout << "Import section name: " << image.section_from_directory(pe_win::image_directory_entry_import).get_name() << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcproj b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..e4f12f28aee3e567003892b89c3155ff5ee15625
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="sections_and_addresses"
+	ProjectGUID="{660117AA-6B9E-4C7D-B0BE-DE6BD17DBA1E}"
+	RootNamespace="sections_and_addresses"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcxproj b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..684a43f1318c897c3c4ebbbd81a09d1ac9f9a7d4
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{99F41F8F-44DB-410E-9883-A6A16E903DF8}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>sections_and_addresses</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/sections_and_addresses/sections_and_addresses.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/tls_editor/Makefile b/irdb-lib/pebliss/trunk/samples/tls_editor/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_editor/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/tls_editor/main.cpp b/irdb-lib/pebliss/trunk/samples/tls_editor/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..700a9fc481d24743d6f0b7c7754e7f51ae2d769d
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_editor/main.cpp
@@ -0,0 +1,88 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как редактировать TLS (Thread Local Storage) у PE-файлов
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: tls_editor.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		//Получим информацию о TLS PE-файла
+		//Если TLS нет, этот вызов выбросит исключение
+		tls_info info(get_tls_info(image));
+		
+		//Пересоберем TLS
+		//Он, вероятно, будет иметь больший размер, чем до нашего редактирования,
+		//поэтому запишем его в новую секцию, чтобы все поместилось
+		//(мы не можем расширять существующие секции, если только секция не в самом конце файла)
+		section new_tls;
+		new_tls.get_raw_data().resize(1); //Мы не можем добавлять пустые секции, поэтому пусть у нее будет начальный размер данных 1
+		new_tls.set_name("new_tls"); //Имя секции
+		new_tls.readable(true); //Доступна на чтение
+		section& attached_section = image.add_section(new_tls); //Добавим секцию и получим ссылку на добавленную секцию с просчитанными размерами
+
+		if(info.get_callbacks_rva() != 0) //Если у TLS есть хотя бы один коллбек
+			info.add_tls_callback(0x100); //Добавим новый коллбек в TLS - относительный адрес, скорее всего, некорректен, поэтому программа не запустится (просто для примера)
+
+		info.set_raw_data("Hello, world!"); //Установим или заменим "сырые" данные TLS
+		info.set_raw_data_start_rva(image.rva_from_section_offset(attached_section, 0)); //Расположим их с начала добавленной секции
+		info.recalc_raw_data_end_rva(); //Просчитаем новый конечный адрес "сырых" данных
+
+		//Пересобираем TLS, расположив их с 50-го байта (будет выровнено, секция будет автоматически расширена) новой секции и записав новые данные TLS в PE-заголовок
+		//По умолчанию функция пересобирает также TLS-коллбеки и "сырые" данные TLS, располагая их по указанным в структуре info адресам
+		//Опция expand позволяет задать, как должны распологаться "сырые" данные
+		//tls_data_expand_raw позволяет увеличить "сырой" размер секции, то есть размер в файле
+		//tls_data_expand_virtual позволяет увеличить виртуальный размер секции с данными TLS
+		//Если не хватит места под данные TLS, будет записана только их часть, или вообще ничего записано не будет
+		rebuild_tls(image, info, attached_section, 50); 
+
+		//Создаем новый PE-файл
+		std::string base_file_name(argv[1]);
+		std::string::size_type slash_pos;
+		if((slash_pos = base_file_name.find_last_of("/\\")) != std::string::npos)
+			base_file_name = base_file_name.substr(slash_pos + 1);
+
+		base_file_name = "new_" + base_file_name;
+		std::ofstream new_pe_file(base_file_name.c_str(), std::ios::out | std::ios::binary | std::ios::trunc);
+		if(!new_pe_file)
+		{
+			std::cout << "Cannot create " << base_file_name << std::endl;
+			return -1;
+		}
+
+		//Пересобираем PE-файл
+		rebuild_pe(image, new_pe_file);
+
+		std::cout << "PE was rebuilt and saved to " << base_file_name << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcproj b/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..249379c497facc0968f8e49e620a03f8576c94b2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="tls_editor"
+	ProjectGUID="{781B56DF-15CE-4CBA-A008-0403029E558A}"
+	RootNamespace="tls_editor"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcxproj b/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..cf2f3b9195050f2519ceb95eb29c2965e2a021c0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{ABA9C7BF-D145-4066-8E0D-41C190BB5C0A}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>tls_editor</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_editor/tls_editor.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/tls_reader/Makefile b/irdb-lib/pebliss/trunk/samples/tls_reader/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..91d2ea5d90ed8ba9bfa09dd3d6ebfdd0934df9df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_reader/Makefile
@@ -0,0 +1 @@
+include ../sample.mak
diff --git a/irdb-lib/pebliss/trunk/samples/tls_reader/main.cpp b/irdb-lib/pebliss/trunk/samples/tls_reader/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..4f5021ae4107a587d9d0d3ff80f643a05db06aba
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_reader/main.cpp
@@ -0,0 +1,58 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+//Пример, показывающий, как считать и получить информацию о статическом TLS (Thread Local Storage, локальная память потока)
+//PE или PE+ файла
+int main(int argc, char* argv[])
+{
+	if(argc != 2)
+	{
+		std::cout << "Usage: tls_reader.exe PE_FILE" << std::endl;
+		return 0;
+	}
+
+	//Открываем файл
+	std::ifstream pe_file(argv[1], std::ios::in | std::ios::binary);
+	if(!pe_file)
+	{
+		std::cout << "Cannot open " << argv[1] << std::endl;
+		return -1;
+	}
+
+	try
+	{
+		//Создаем экземпляр PE или PE+ класса с помощью фабрики
+		pe_base image(pe_factory::create_pe(pe_file));
+
+		std::cout << "Reading PE TLS info..." << std::hex << std::showbase << std::endl << std::endl;
+		
+		//Получаем информацию о TLS
+		const tls_info info = get_tls_info(image);
+
+		//Выводим информацию о TLS
+		std::cout << "Callbacks RVA: " << info.get_callbacks_rva() << std::endl
+			<< "Index RVA: " << info.get_index_rva() << std::endl
+			<< "Raw data start RVA: " << info.get_raw_data_start_rva() << std::endl
+			<< "Raw data end RVA: " << info.get_raw_data_end_rva() << std::endl
+			<< "Size of zero fill: " << info.get_size_of_zero_fill() << std::endl;
+
+		//Выведем TLS-коллбеки:
+		const tls_info::tls_callback_list& tls_callbacks = info.get_tls_callbacks();
+		for(tls_info::tls_callback_list::const_iterator it = tls_callbacks.begin(); it != tls_callbacks.end(); ++it)
+			std::cout << "Callback: " << (*it) << std::endl;
+	}
+	catch(const pe_exception& e)
+	{
+		//Если возникла ошибка
+		std::cout << "Error: " << e.what() << std::endl;
+		return -1;
+	}
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcproj b/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..7ff7bf6616ef86271700c149fbf3cee45e2bce29
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="tls_reader"
+	ProjectGUID="{BA36739B-F101-4C91-928D-678AB9521A22}"
+	RootNamespace="tls_reader"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcxproj b/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..0ab9a5e51f504047aa2d7d2cc75a589fa6aab423
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcxproj
@@ -0,0 +1,158 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{CFB9A225-E2E5-43BC-898A-6D52357E7F92}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>tls_reader</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+    <CodeAnalysisRuleSet>AllRules.ruleset</CodeAnalysisRuleSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <EnablePREfast>false</EnablePREfast>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcxproj.filters b/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..33c9b83ec121a2f99a3c03bf1b76e0fac37d8d64
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/samples/tls_reader/tls_reader.vcxproj.filters
@@ -0,0 +1,27 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/Makefile b/irdb-lib/pebliss/trunk/tests/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..ab12c166d274c2c4d3ee5b268c9966a691e2b2d7
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/Makefile
@@ -0,0 +1,21 @@
+TESTS = tests_utils tests_basic test_rich_data test_entropy test_runner test_checksum test_tls test_relocations test_load_config test_exception_directory test_imports test_exports test_resources test_bound_import test_resource_viewer test_dotnet test_debug test_resource_manager test_resource_bitmap test_resource_icon_cursor test_resource_string_table test_resource_message_table test_resource_version_info
+OUTDIR = ./bin/
+LIBPATH = ../lib/libpebliss.a
+TARGETS = $(foreach test,$(TESTS),$(test)_test)
+TARGETS_CLEAN = $(foreach test,$(TESTS),$(test)_clean)
+
+all: $(TARGETS) run_all_tests
+
+clean: $(TARGETS_CLEAN)
+
+$(OUTDIR):
+	mkdir -p $(OUTDIR)
+
+%_test: $(OUTDIR) $(LIBPATH)
+	$(MAKE) PE_DEBUG=$(PE_DEBUG) -C ./$*
+	
+%_clean:
+	$(MAKE) -C ./$* clean
+
+run_all_tests:
+	./bin/test_runner
diff --git a/irdb-lib/pebliss/trunk/tests/lib.h b/irdb-lib/pebliss/trunk/tests/lib.h
new file mode 100644
index 0000000000000000000000000000000000000000..27d33526d5ecbf057866415831032aede4ce6cb9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/lib.h
@@ -0,0 +1,14 @@
+#pragma once
+#ifndef _M_X64
+#ifdef _DEBUG
+#pragma comment(lib, "../../Debug/pe_bliss.lib")
+#else
+#pragma comment(lib, "../../Release/pe_bliss.lib")
+#endif
+#else
+#ifdef _DEBUG
+#pragma comment(lib, "../../x64/Debug/pe_bliss.lib")
+#else
+#pragma comment(lib, "../../x64/Release/pe_bliss.lib")
+#endif
+#endif
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/TestApp.exe b/irdb-lib/pebliss/trunk/tests/pe_files/TestApp.exe
new file mode 100644
index 0000000000000000000000000000000000000000..c9487ab657b050ec13d66137ebb4894f7ca74b17
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/TestApp.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/bound32.exe b/irdb-lib/pebliss/trunk/tests/pe_files/bound32.exe
new file mode 100644
index 0000000000000000000000000000000000000000..1d593d3e0384afd81e78c64c24eaf5ba13f0eec6
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/bound32.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/bound64.exe b/irdb-lib/pebliss/trunk/tests/pe_files/bound64.exe
new file mode 100644
index 0000000000000000000000000000000000000000..e288befc9b9f38bf8854a8c4ad36c5958700139f
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/bound64.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/debug_test.exe b/irdb-lib/pebliss/trunk/tests/pe_files/debug_test.exe
new file mode 100644
index 0000000000000000000000000000000000000000..0dd38a057d04a80045bd0c89041b9dbbfb281d0b
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/debug_test.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/image32.exe b/irdb-lib/pebliss/trunk/tests/pe_files/image32.exe
new file mode 100644
index 0000000000000000000000000000000000000000..fab6f99f62f9e3733f3c7150d9125738062f8880
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/image32.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/image64.exe b/irdb-lib/pebliss/trunk/tests/pe_files/image64.exe
new file mode 100644
index 0000000000000000000000000000000000000000..5f426f7f26598bff141eecdb5a2ed43313d47643
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/image64.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/message_table_resource.exe b/irdb-lib/pebliss/trunk/tests/pe_files/message_table_resource.exe
new file mode 100644
index 0000000000000000000000000000000000000000..b28bd212a1a89e01445db69d7ef9ad94943b8cb4
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/message_table_resource.exe differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/test_dll_32.dll b/irdb-lib/pebliss/trunk/tests/pe_files/test_dll_32.dll
new file mode 100644
index 0000000000000000000000000000000000000000..5f9a485e00e147d79bd505020578dccac1f29e41
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/test_dll_32.dll differ
diff --git a/irdb-lib/pebliss/trunk/tests/pe_files/test_dll_64.dll b/irdb-lib/pebliss/trunk/tests/pe_files/test_dll_64.dll
new file mode 100644
index 0000000000000000000000000000000000000000..2bbcfcc401474468ee0ec92c8d187da60c0887af
Binary files /dev/null and b/irdb-lib/pebliss/trunk/tests/pe_files/test_dll_64.dll differ
diff --git a/irdb-lib/pebliss/trunk/tests/test.h b/irdb-lib/pebliss/trunk/tests/test.h
new file mode 100644
index 0000000000000000000000000000000000000000..032214812ab04d1c736ff04254f62eac944cd414
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test.h
@@ -0,0 +1,124 @@
+#pragma once
+#include <string>
+#include <iostream>
+#include <typeinfo>
+#include <exception>
+#include <stdlib.h>
+
+enum test_level
+{
+	test_level_normal,
+	test_level_critical
+};
+
+static void pe_test_print_error(const std::string& test_name,
+	test_level level,
+	const std::string& expression,
+	const std::string& file, size_t line)
+{
+	std::cerr << test_name << " - FAIL!" << std::endl
+		<< "File: " << file << ", line: " << line << std::endl
+		<< "Expression: " << expression << std::endl << std::endl;
+
+	if(level == test_level_critical)
+		exit(EXIT_FAILURE);
+}
+
+static void pe_test(bool result,
+	const std::string& test_name, test_level level,
+	const std::string& expression,
+	const std::string& file, size_t line)
+{
+	if(result)
+		std::cout << test_name << " - OK" << std::endl;
+	else
+		pe_test_print_error(test_name, level, expression, file, line);
+}
+
+static void pe_test_error(const std::exception& e,
+	const std::string& test_name, test_level level,
+	const std::string& expression,
+	const std::string& file, size_t line)
+{
+	std::cerr << test_name << " FAIL!" << std::endl
+		<< "File: " << file << ", line: " << line << std::endl
+		<< "Expression: " << expression << std::endl
+		<< "Exception occured: " << e.what() << std::endl
+		<< "Exception type: " << typeid(e).name() << std::endl << std::endl;
+
+	if(level == test_level_critical)
+		exit(EXIT_FAILURE);
+}
+
+#define PE_TEST_TO_STRING(expression) #expression
+
+//Checks the result of expression (true)
+#define PE_TEST(expression, test_name, level) \
+	try \
+	{ \
+		pe_test((expression), test_name, level, PE_TEST_TO_STRING(expression), __FILE__, __LINE__); \
+	} \
+	catch(const std::exception& e) \
+	{ \
+		pe_test_error(e, test_name, level, PE_TEST_TO_STRING(expression), __FILE__, __LINE__); \
+	}
+
+//Runs expression and checks for exceptions
+#define PE_TEST_EXCEPTION(expression, test_name, level) \
+	try \
+	{ \
+		(expression); \
+		std::cout << test_name << " - OK" << std::endl; \
+	} \
+	catch(const std::exception& e) \
+	{ \
+		pe_test_error(e, test_name, level, PE_TEST_TO_STRING(expression), __FILE__, __LINE__); \
+	}
+
+//Awaits exception from expression
+#define PE_TEST_EXPECT_EXCEPTION(expression, pe_exception_code, test_name, level) \
+	try \
+	{ \
+		(expression); \
+		std::cerr << "Expected exception: " << PE_TEST_TO_STRING(pe_exception_code) << std::endl; \
+		pe_test_print_error(test_name, level, PE_TEST_TO_STRING(expression), __FILE__, __LINE__); \
+	} \
+	catch(const pe_exception& e) \
+	{ \
+		if(e.get_id() == pe_exception_code) \
+			std::cout << test_name << " - OK" << std::endl; \
+		else \
+			pe_test_error(e, test_name, level, PE_TEST_TO_STRING(expression), __FILE__, __LINE__); \
+	}
+
+
+#ifndef PE_FILES_UNUSED
+static bool open_pe_file(int argc, char* argv[], std::auto_ptr<std::ifstream>& pe_file)
+{
+	if(argc != 2)
+	{
+		std::cerr << "Usage: test.exe PE_FILE" << std::endl;
+		return false;
+	}
+	
+	pe_file.reset(new std::ifstream(argv[1], std::ios::in | std::ios::binary));
+	if(!*pe_file)
+	{
+		std::cerr << "Cannot open " << argv[1] << std::endl;
+		return false;
+	}
+
+	return true;
+}
+#endif
+
+#define PE_TEST_START \
+	try \
+	{
+
+
+#define PE_TEST_END } \
+	catch(const std::exception& e) \
+	{ \
+		pe_test_error(e, "Global Test", test_level_critical, "global test exception handler", __FILE__, __LINE__); \
+	}
diff --git a/irdb-lib/pebliss/trunk/tests/test_bound_import/Makefile b/irdb-lib/pebliss/trunk/tests/test_bound_import/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_bound_import/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_bound_import/main.cpp b/irdb-lib/pebliss/trunk/tests/test_bound_import/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..69b9cb937292c66e151cc5e4776d41702f59a162
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_bound_import/main.cpp
@@ -0,0 +1,83 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void test_bound_imports(const pe_base& image)
+{
+	bound_import_module_list imports;
+	PE_TEST_EXCEPTION(imports = get_bound_import_module_list(image), "Bound Import Parser test", test_level_critical);
+	PE_TEST(imports.size() == 2, "Bound Import test 1", test_level_critical);
+	PE_TEST(imports[0].get_module_name() == "USER32.dll"
+		&& imports[1].get_module_name() == "KERNEL32.dll", "Bound Import test 2", test_level_normal);
+
+	if(image.get_pe_type() == pe_type_32)
+	{
+		PE_TEST(imports[0].get_timestamp() == 0x4a5bdb3c
+			&& imports[1].get_timestamp() == 0x4afc68c0, "Bound Import test 3", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(imports[0].get_timestamp() == 0x4a5bdb3c
+			&& imports[1].get_timestamp() == 0, "Bound Import test 3", test_level_normal);
+	}
+
+	PE_TEST(imports[0].get_module_ref_count() == 0
+		&& imports[1].get_module_ref_count() == 1, "Bound Import test 4", test_level_critical);
+	PE_TEST(imports[1].get_module_ref_list()[0].get_module_name() == "NTDLL.DLL"
+		&& imports[1].get_module_ref_list()[0].get_timestamp() == 0x4afc681b, "Bound Import test 5", test_level_normal);
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	test_bound_imports(image);
+
+	{
+		std::stringstream new_pe(std::ios::in | std::ios::out | std::ios::binary);
+		PE_TEST_EXCEPTION(rebuild_pe(image, new_pe, false, true, true), "Bound Rebuild PE test 1", test_level_critical);
+		PE_TEST_EXCEPTION(image = pe_factory::create_pe(new_pe), "Bound Rebuild PE test 2", test_level_critical);
+		test_bound_imports(image);
+		
+		new_pe.str("");
+		PE_TEST_EXCEPTION(rebuild_pe(image, new_pe, true, true, true), "Bound Rebuild PE test 3", test_level_critical);
+		PE_TEST_EXCEPTION(image = pe_factory::create_pe(new_pe), "Bound Rebuild PE test 4", test_level_critical);
+		test_bound_imports(image);
+	}
+
+	
+	section s;
+	s.get_raw_data().resize(1);
+	s.set_name("newbound");
+	s.readable(true);
+	section& new_bound_import_section = image.add_section(s);
+	bound_import_module_list imports;
+	PE_TEST_EXCEPTION(imports = get_bound_import_module_list(image), "Bound Import Parser test", test_level_critical);
+	
+	uint32_t old_bound_import_rva = image.get_directory_rva(pe_win::image_directory_entry_bound_import);
+	PE_TEST_EXCEPTION(rebuild_bound_imports(image, imports, new_bound_import_section, 0, true, true), "Bound Import Rebuilder test 1", test_level_critical);
+	PE_TEST(old_bound_import_rva != image.get_directory_rva(pe_win::image_directory_entry_bound_import), "Bound Import Directory test", test_level_normal);
+	test_bound_imports(image);
+	
+	new_bound_import_section.set_raw_data("111");
+	old_bound_import_rva = image.get_directory_rva(pe_win::image_directory_entry_bound_import);
+	PE_TEST_EXCEPTION(rebuild_bound_imports(image, imports, new_bound_import_section, 3, true, true), "Bound Import Rebuilder test 2", test_level_critical);
+	PE_TEST(new_bound_import_section.get_raw_data().substr(0, 3) == "111", "Bound Import Rebuilder Offset test", test_level_normal);
+	PE_TEST(old_bound_import_rva != image.get_directory_rva(pe_win::image_directory_entry_bound_import), "Bound Import Directory test 2", test_level_normal);
+	test_bound_imports(image);
+	
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcproj b/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..d3b1e34b2757741ccfd3eb5c9f6a095b0941179f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_bound_import"
+	ProjectGUID="{6EBEAFA6-7489-4026-83D1-CAF67D243119}"
+	RootNamespace="test_bound_import"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcxproj b/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..1016788db89add3aaa45d3f4556860ee95eaf3d8
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcxproj
@@ -0,0 +1,163 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{DA8A8F03-E719-45EF-A376-766A18772FA5}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_bound_import</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8755a3a0268981c2f6fee186ee23f9488c6d781c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_bound_import/test_bound_import.vcxproj.filters
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_checksum/Makefile b/irdb-lib/pebliss/trunk/tests/test_checksum/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_checksum/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_checksum/main.cpp b/irdb-lib/pebliss/trunk/tests/test_checksum/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..6fc33b1f8bdd6e101db36a982edb2e0b76020306
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_checksum/main.cpp
@@ -0,0 +1,28 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	uint32_t checksum = -1;
+	PE_TEST_EXCEPTION(checksum = calculate_checksum(*pe_file), "Checksum test 1", test_level_normal);
+	PE_TEST(image.get_checksum() == checksum, "Checksum test 2", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcproj b/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..b40b3542d35f4c506a79c9c4cd2b9f225648d3d1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_checksum"
+	ProjectGUID="{7F95DC75-2CFA-4D0D-BD43-1BF6749F16EE}"
+	RootNamespace="test_checksum"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcxproj b/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..00822bc45c6dc5ab71855f9207c1927241d5bc48
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcxproj
@@ -0,0 +1,168 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{7B7AEAB2-7755-409D-A6C9-D5FFB7D1A95A}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_other</RootNamespace>
+    <ProjectName>test_checksum</ProjectName>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_checksum/test_checksum.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_debug/Makefile b/irdb-lib/pebliss/trunk/tests/test_debug/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_debug/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_debug/main.cpp b/irdb-lib/pebliss/trunk/tests/test_debug/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..77f010dc76115884b5ba8f6a041cdf0cb3e70441
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_debug/main.cpp
@@ -0,0 +1,122 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void debug_test(const debug_info& dbg)
+{
+	PE_TEST(dbg.get_characteristics() == 0
+		&& dbg.get_time_stamp() == 0x50757757
+		&& dbg.get_major_version() == 0
+		&& dbg.get_minor_version() == 0
+		&& dbg.get_rva_of_raw_data() == 0,
+		"Debug Basic Info test", test_level_normal);
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	debug_info_list info;
+	PE_TEST_EXCEPTION(info = get_debug_information(image), "Debug Info Parser test", test_level_critical);
+
+	if(image.get_pe_type() == pe_type_32)
+	{
+		{
+			PE_TEST(info.size() == 3, "Debug Info test 1", test_level_critical);
+			debug_info& dbg = info[0];
+			debug_test(dbg);
+			PE_TEST(dbg.get_size_of_data() == 0x00008CB1, "Debug Info test 2", test_level_normal);
+
+			PE_TEST(dbg.get_type() == debug_info::debug_type_coff
+				&& dbg.get_advanced_info_type() == debug_info::advanced_info_coff, "Debug Info test 3", test_level_critical);
+
+			coff_debug_info advanced;
+			PE_TEST_EXCEPTION(advanced = dbg.get_advanced_debug_info<coff_debug_info>(), "Debug COFF Info Parser test", test_level_critical);
+			PE_TEST(advanced.get_number_of_line_numbers() == 0
+				&& advanced.get_number_of_symbols() == 0x4E9, "Debug Info test 4", test_level_critical);
+			PE_TEST(advanced.get_lva_to_first_line_number() == 0
+				&& advanced.get_lva_to_first_symbol() == 0x20
+				&& advanced.get_rva_to_first_byte_of_code() == 0x1000
+				&& advanced.get_rva_to_first_byte_of_data() == 0xE000
+				&& advanced.get_rva_to_last_byte_of_code() == 0xE000
+				&& advanced.get_rva_to_last_byte_of_data() == 0x7000, "Debug Info test 5", test_level_normal);
+
+			const coff_debug_info::coff_symbol& sym = advanced.get_symbols()[1];
+			PE_TEST(sym.get_index() == 0x55 && sym.get_rva() == 0xCD1C
+				&& sym.get_section_number() == 1
+				&& sym.get_storage_class() == 3
+				&& sym.get_type() == 0
+				&& !sym.is_file()
+				&& sym.get_symbol() == "UnwindUpVec", "Debug Info test 6", test_level_normal);
+		}
+
+		{
+			debug_info& dbg = info[1];
+			debug_test(dbg);
+			PE_TEST(dbg.get_size_of_data() == 0x110, "Debug Info test 7", test_level_normal);
+
+			PE_TEST(dbg.get_type() == debug_info::debug_type_misc
+				&& dbg.get_advanced_info_type() == debug_info::advanced_info_misc, "Debug Info test 8", test_level_critical);
+
+			misc_debug_info advanced;
+			PE_TEST_EXCEPTION(advanced = dbg.get_advanced_debug_info<misc_debug_info>(), "Debug MISC Info Parser test", test_level_critical);
+			PE_TEST(advanced.is_exe_name(), "Debug MISC test 1", test_level_normal);
+			PE_TEST(!advanced.is_unicode(), "Debug MISC test 2", test_level_normal);
+			PE_TEST(advanced.get_data_ansi() == "Debug/debugtest.exe", "Debug MISC test 3", test_level_normal);
+		}
+
+		{
+			debug_info& dbg = info[2];
+			debug_test(dbg);
+			PE_TEST(dbg.get_size_of_data() == 0x68, "Debug Info test 9", test_level_normal);
+
+			PE_TEST(dbg.get_type() == debug_info::debug_type_codeview
+				&& dbg.get_advanced_info_type() == debug_info::advanced_info_pdb_2_0, "Debug Info test 10", test_level_critical);
+
+			pdb_2_0_info advanced;
+			PE_TEST_EXCEPTION(advanced = dbg.get_advanced_debug_info<pdb_2_0_info>(), "Debug PDB 2.0 Info Parser test", test_level_critical);
+			PE_TEST(advanced.get_age() == 1, "Debug PDB 2.0 test 1", test_level_normal);
+			PE_TEST(advanced.get_signature() == 0x50757757, "Debug PDB 2.0 test 2", test_level_normal);
+			PE_TEST(advanced.get_pdb_file_name() == "C:\\Program Files (x86)\\Microsoft Visual Studio\\MyProjects\\debugtest\\Debug\\debugtest.pdb", "Debug PDB 2.0 test 3", test_level_normal);
+		}
+	}
+	else
+	{
+		PE_TEST(info.size() == 1, "Debug Info test 1", test_level_critical);
+		debug_info& dbg = info[0];
+		PE_TEST(dbg.get_characteristics() == 0
+			&& dbg.get_time_stamp() == 0x50937d36
+			&& dbg.get_major_version() == 0
+			&& dbg.get_minor_version() == 0
+			&& dbg.get_rva_of_raw_data() == 0x0001F300
+			&& dbg.get_size_of_data() == 0x0000006F,
+			"Debug Basic Info test", test_level_normal);
+
+		PE_TEST(dbg.get_type() == debug_info::debug_type_codeview
+			&& dbg.get_advanced_info_type() == debug_info::advanced_info_pdb_7_0, "Debug Info test 2", test_level_critical);
+
+		pdb_7_0_info advanced;
+		PE_TEST_EXCEPTION(advanced = dbg.get_advanced_debug_info<pdb_7_0_info>(), "Debug PDB 7.0 Info Parser test", test_level_critical);
+		PE_TEST(advanced.get_age() == 1, "Debug PDB 7.0 test 1", test_level_normal);
+
+		pe_win::guid testguid = {0xCC311030, 0xD245, 0x4FF7, {0x9F, 0x16, 0xB5, 0x6D, 0x8B, 0x11, 0x1F, 0x1A}};
+		PE_TEST(advanced.get_guid() == testguid, "Debug PDB 7.0 test 2", test_level_normal);
+		PE_TEST(advanced.get_pdb_file_name() == "C:\\Users\\Bliss\\Documents\\Visual Studio 2010\\Projects\\hello_world\\x64\\Release\\test1.pdb", "Debug PDB 7.0 test 3", test_level_normal);
+	}
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcproj b/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..a2aac4b0d0e9f9dcc266f71cb21994a1cc830008
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_debug"
+	ProjectGUID="{42AC1521-0800-4D81-9363-6EF9362F7A4A}"
+	RootNamespace="test_debug"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcxproj b/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..4de2d750a924a36f7b577ca457c567526de7f3ad
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{B82FC407-B927-49D1-9DEB-0DFC3DC12A9C}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_debug</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_debug/test_debug.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_dotnet/Makefile b/irdb-lib/pebliss/trunk/tests/test_dotnet/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_dotnet/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_dotnet/main.cpp b/irdb-lib/pebliss/trunk/tests/test_dotnet/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..d5ec9b37aced4e7f087f7793d9d2550d6099f8eb
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_dotnet/main.cpp
@@ -0,0 +1,39 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	basic_dotnet_info info;
+	PE_TEST_EXCEPTION(info = get_basic_dotnet_info(image), "Basic Dotnet Info Parser test", test_level_critical);
+	PE_TEST(info.get_flags() == 1, "DotNet test 1", test_level_normal);
+	PE_TEST(info.get_major_runtime_version() == 2 && info.get_minor_runtime_version() == 5, "DotNet test 2", test_level_normal);
+	PE_TEST(info.get_rva_of_metadata() == 0x2064 && info.get_size_of_metadata() == 0x598, "DotNet test 3", test_level_normal);
+	PE_TEST(info.get_rva_of_resources() == 0 && info.get_size_of_resources() == 0, "DotNet test 4", test_level_normal);
+	PE_TEST(info.get_rva_of_strong_name_signature() == 0 && info.get_size_of_strong_name_signature() == 0, "DotNet test 5", test_level_normal);
+	PE_TEST(info.get_rva_of_code_manager_table() == 0 && info.get_size_of_code_manager_table() == 0, "DotNet test 6", test_level_normal);
+	PE_TEST(info.get_rva_of_vtable_fixups() == 0 && info.get_size_of_vtable_fixups() == 0, "DotNet test 7", test_level_normal);
+	PE_TEST(info.get_rva_of_export_address_table_jumps() == 0 && info.get_size_of_export_address_table_jumps() == 0, "DotNet test 8", test_level_normal);
+	PE_TEST(info.get_rva_of_managed_native_header() == 0 && info.get_size_of_managed_native_header() == 0, "DotNet test 9", test_level_normal);
+	PE_TEST(info.get_entry_point_rva_or_token() == 0x06000001, "DotNet test 10", test_level_normal);
+	PE_TEST(!info.is_native_entry_point(), "DotNet test 11", test_level_normal);
+	PE_TEST(!info.is_32bit_required(), "DotNet test 12", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcproj b/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..40fcfc8f824b3347217698567822fccd119ba210
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_dotnet"
+	ProjectGUID="{094A7331-54E1-4034-BD1E-BE2F974B0142}"
+	RootNamespace="test_dotnet"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcxproj b/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..41ff9fca4dead700260d0f59da90b074f0b52083
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcxproj
@@ -0,0 +1,168 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{F8A9C956-AA19-4AEF-B1B7-E7C392E437FE}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_dotner</RootNamespace>
+    <ProjectName>test_dotnet</ProjectName>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_dotnet/test_dotnet.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_entropy/Makefile b/irdb-lib/pebliss/trunk/tests/test_entropy/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_entropy/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_entropy/main.cpp b/irdb-lib/pebliss/trunk/tests/test_entropy/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..3bb6d116e6f7694cc9bf48f1b335b738c7e7a9b2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_entropy/main.cpp
@@ -0,0 +1,34 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	PE_TEST(entropy_calculator::calculate_entropy(image) > 3.0, "Entropy test 1", test_level_normal);
+	PE_TEST(entropy_calculator::calculate_entropy(*pe_file) > 3.0, "Entropy test 2", test_level_normal);
+	PE_TEST(entropy_calculator::calculate_entropy(image.get_image_sections().at(0)) > 3.0, "Entropy test 3", test_level_normal);
+
+	const char data[] = "123456789";
+	PE_TEST(entropy_calculator::calculate_entropy(data, sizeof(data) - 1) > 3.0, "Entropy test 4", test_level_normal);
+
+	PE_TEST_EXPECT_EXCEPTION(entropy_calculator::calculate_entropy("", 0), pe_exception::data_is_empty, "Entropy test 5", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(entropy_calculator::calculate_entropy(section()), pe_exception::section_is_empty, "Entropy test 6", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcproj b/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..1b1287445d4b3d4a0d278979af3cdfb4655a6442
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_entropy"
+	ProjectGUID="{D3FAD2A8-FF48-4E59-A347-C54AD9DB6AC4}"
+	RootNamespace="test_entropy"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcxproj b/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..8cfdcdb616bb75e08075f973b1e95c810e4d3e22
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{853CFFF4-1FAB-48EB-81A9-CC35F9FB3F80}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_entropy</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_entropy/test_entropy.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_exception_directory/Makefile b/irdb-lib/pebliss/trunk/tests/test_exception_directory/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exception_directory/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_exception_directory/main.cpp b/irdb-lib/pebliss/trunk/tests/test_exception_directory/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..f8521eaed3517175822d595cc444a2c7c9d6c681
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exception_directory/main.cpp
@@ -0,0 +1,40 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	if(image.get_pe_type() == pe_type_64)
+	{
+		exception_entry_list info;
+		PE_TEST_EXCEPTION(info = get_exception_directory_data(image), "Exception directory parser test", test_level_critical);
+		PE_TEST(info.size() == 0x1C6, "Exception directory test 1", test_level_normal);
+		PE_TEST(info[5].get_begin_address() == 0x000011D5
+			&& info[5].get_end_address() == 0x00001220, "Exception directory test 2", test_level_normal);
+		PE_TEST(info[5].get_flags() == 4, "Exception directory test 3", test_level_normal);
+		PE_TEST(info[5].get_unwind_info_address() == 0x21528, "Exception directory test 4", test_level_normal);
+		PE_TEST(info[5].get_unwind_info_version() == 1, "Exception directory test 5", test_level_normal);
+		PE_TEST(info[5].get_size_of_prolog() == 0x5, "Exception directory test 6", test_level_normal);
+		PE_TEST(info[5].get_number_of_unwind_slots() == 2, "Exception directory test 7", test_level_normal);
+		PE_TEST(info[5].get_frame_pointer_register_number() == 0, "Exception directory test 8", test_level_normal);
+		PE_TEST(info[5].get_scaled_rsp_offset() == 0, "Exception directory test 9", test_level_normal);
+	}
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcproj b/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..91d5bde30c1de0690215a6400087bf12ffdf35cf
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_exception_directory"
+	ProjectGUID="{1C36ED94-CBE5-4107-83B6-9C37F3A4041C}"
+	RootNamespace="test_exception_directory"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcxproj b/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..03fcdf08b808ea474b6b57257c798fa1304ed66c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{B6A37BAA-484D-4175-BEA2-62892A12E8F5}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_exception_directory</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exception_directory/test_exception_directory.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_exports/Makefile b/irdb-lib/pebliss/trunk/tests/test_exports/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exports/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_exports/main.cpp b/irdb-lib/pebliss/trunk/tests/test_exports/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..23965cf09c89cca67ce425b9d31c2dbcd5bf62df
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exports/main.cpp
@@ -0,0 +1,147 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void test_exports(const export_info& info, const exported_functions_list& exports, const pe_base& image, bool test_rvas = true)
+{
+	PE_TEST(info.get_characteristics() == 0
+		&& info.get_major_version() == 0
+		&& info.get_minor_version() == 0
+		&& info.get_ordinal_base() == 5
+		&& info.get_name() == "test_dll.dll"
+		&& info.get_number_of_functions() == 6
+		&& info.get_number_of_names() == 3, "Exports test 1", test_level_normal);
+
+	if(test_rvas)
+	{
+		if(image.get_pe_type() == pe_type_32)
+		{
+			PE_TEST(info.get_timestamp() == 0x509103D8
+				&& info.get_rva_of_functions() == 0x00002588
+				&& info.get_rva_of_names() == 0x000025A0
+				&& info.get_rva_of_name_ordinals() == 0x000025AC, "Exports test 2", test_level_normal);
+		}
+		else
+		{
+			PE_TEST(info.get_timestamp() == 0x509103D3
+				&& info.get_rva_of_functions() == 0x00002718
+				&& info.get_rva_of_names() == 0x00002730
+				&& info.get_rva_of_name_ordinals() == 0x0000273C, "Exports test 2", test_level_normal);
+		}
+	}
+
+	PE_TEST(exports.size() == 4, "Exports test 3", test_level_critical);
+
+	PE_TEST(exports[0].has_name() && exports[0].get_name() == "dll_func1", "Exports test 4", test_level_normal);
+	PE_TEST(!exports[0].is_forwarded(), "Exports test 5", test_level_normal);
+	PE_TEST(exports[0].get_name_ordinal() == 0 && exports[0].get_ordinal() == 5, "Exports test 6", test_level_normal);
+	PE_TEST(exports[0].get_rva() == 0x00001000, "Exports test 7", test_level_normal);
+
+	PE_TEST(exports[2].has_name() && exports[2].get_name() == "MsgBoxA", "Exports test 8", test_level_normal);
+	PE_TEST(exports[2].is_forwarded() && exports[2].get_forwarded_name() == "USER32.MessageBoxA", "Exports test 9", test_level_normal);
+	PE_TEST(exports[2].get_name_ordinal() == 2 && exports[2].get_ordinal() == 7, "Exports test 10", test_level_normal);
+
+	if(test_rvas)
+	{
+		if(image.get_pe_type() == pe_type_32)
+		{
+			PE_TEST(exports[2].get_rva() == 0x000025DB, "Exports test 11", test_level_normal);
+		}
+		else
+		{
+			PE_TEST(exports[2].get_rva() == 0x0000276B, "Exports test 11", test_level_normal);
+		}
+	}
+
+	PE_TEST(!exports[3].has_name() && exports[3].get_ordinal() == 0xA, "Exports test 12", test_level_normal);
+	PE_TEST(!exports[3].is_forwarded(), "Exports test 13", test_level_normal);
+	PE_TEST(exports[3].get_rva() == 0x00001020, "Exports test 14", test_level_normal);
+
+	std::pair<uint16_t, uint16_t> limits;
+	PE_TEST_EXCEPTION(limits = get_export_ordinal_limits(exports), "get_export_ordinal_limits test 1", test_level_normal);
+	PE_TEST(limits.first == info.get_ordinal_base() && limits.second == 0xA, "get_export_ordinal_limits test 2", test_level_normal);
+
+	PE_TEST(exported_name_exists("MsgBoxA", exports), "exported_name_exists test 1", test_level_normal);
+	PE_TEST(exported_name_exists("dll_func1", exports), "exported_name_exists test 2", test_level_normal);
+	PE_TEST(!exported_name_exists("dll_func2", exports), "exported_name_exists test 3", test_level_normal);
+	PE_TEST(!exported_name_exists("USER32.MessageBoxA", exports), "exported_name_exists test 4", test_level_normal);
+
+	PE_TEST(exported_ordinal_exists(0x5, exports), "exported_ordinal_exists test 1", test_level_normal);
+	PE_TEST(exported_ordinal_exists(0xA, exports), "exported_ordinal_exists test 2", test_level_normal);
+	PE_TEST(!exported_ordinal_exists(0x1, exports), "exported_ordinal_exists test 3", test_level_normal);
+	PE_TEST(!exported_ordinal_exists(0x9, exports), "exported_ordinal_exists test 4", test_level_normal);
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	exported_functions_list exports;
+	export_info info;
+	PE_TEST_EXCEPTION(exports = get_exported_functions(image, info), "Exports Parser test 1", test_level_critical);
+	test_exports(info, exports, image);
+
+	PE_TEST_EXCEPTION(rebuild_exports(image, info, exports, image.section_from_directory(pe_win::image_directory_entry_export), 0, true, true), "Exports Rebuilder test 1", test_level_critical);
+	PE_TEST_EXCEPTION(exports = get_exported_functions(image, info), "Exports Parser test 2", test_level_critical);
+	test_exports(info, exports, image, false);
+	
+	section s;
+	s.get_raw_data().resize(1);
+	s.set_name("newexp");
+	section& new_export_section = image.add_section(s);
+	uint32_t old_export_rva = image.get_directory_rva(pe_win::image_directory_entry_export);
+	PE_TEST_EXCEPTION(rebuild_exports(image, info, exports, new_export_section, 0, true, true), "Exports Rebuilder test 2", test_level_critical);
+	PE_TEST(old_export_rva != image.get_directory_rva(pe_win::image_directory_entry_export), "Exports Rebuilder test 3", test_level_normal);
+	PE_TEST_EXCEPTION(exports = get_exported_functions(image, info), "Exports Parser test 3", test_level_critical);
+	test_exports(info, exports, image, false);
+	
+	new_export_section.set_raw_data("111");
+	PE_TEST_EXCEPTION(rebuild_exports(image, info, exports, new_export_section, 3, true, true), "Exports Rebuilder test 4", test_level_critical);
+	PE_TEST(new_export_section.get_raw_data().substr(0, 3) == "111", "Exports Rebuilder offset test 1", test_level_normal);
+	PE_TEST_EXCEPTION(exports = get_exported_functions(image, info), "Exports Parser test 4", test_level_critical);
+	test_exports(info, exports, image, false);
+	
+	new_export_section.set_raw_data("111111111111");
+	PE_TEST_EXCEPTION(rebuild_exports(image, info, exports, new_export_section, 12, true, true), "Exports Rebuilder test 5", test_level_critical);
+	PE_TEST(new_export_section.get_raw_data().substr(0, 12) == "111111111111", "Exports Rebuilder offset test 2", test_level_normal);
+	PE_TEST_EXCEPTION(exports = get_exported_functions(image, info), "Exports Parser test 5", test_level_critical);
+	test_exports(info, exports, image, false);
+
+	exported_function func;
+	func.set_ordinal(0xA);
+	func.set_name("DuplicatedOrdinal");
+	func.set_rva(0x1000);
+	exports.push_back(func);
+	PE_TEST_EXPECT_EXCEPTION(rebuild_exports(image, info, exports, new_export_section, 12, true, true), pe_exception::duplicate_exported_function_ordinal, "Exports Rebuilder test 6", test_level_normal);
+
+	exports.back().set_ordinal(0xC);
+	exports.back().set_name("MsgBoxA"); //Duplicate name
+	PE_TEST_EXPECT_EXCEPTION(rebuild_exports(image, info, exports, new_export_section, 12, true, true), pe_exception::duplicate_exported_function_name, "Exports Rebuilder test 7", test_level_normal);
+	
+	exports.back().set_ordinal(0xC);
+	exports.back().set_name("ANewFunction");
+	exports.back().set_ordinal(0xF);
+	PE_TEST_EXCEPTION(rebuild_exports(image, info, exports, new_export_section, 12, true, true), "Exports Rebuilder test 8", test_level_normal);
+	PE_TEST_EXCEPTION(exports = get_exported_functions(image, info), "Exports Parser test 6", test_level_critical);
+
+	PE_TEST(exports.size() == 5, "New Exported Function test 1", test_level_critical);
+	PE_TEST(exports[4].has_name() && exports[4].get_name() == "ANewFunction", "New Exported Function test 2", test_level_normal);
+	PE_TEST(!exports[4].is_forwarded(), "New Exported Function test 3", test_level_normal);
+	PE_TEST(exports[4].get_rva() == 0x00001000, "New Exported Function test 4", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcproj b/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..af99cbe4cfb8108b675c2c924c03d805a8e494a9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_exports"
+	ProjectGUID="{E126644C-38FF-41EF-9EAF-ED8C9FCF62EF}"
+	RootNamespace="test_exports"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcxproj b/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..d40a35cb422b0704ee279bf2c1b90a4ba4c24c51
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{82EAF17E-9618-4BD7-AE50-0C325591B585}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_exports</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_exports/test_exports.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_imports/Makefile b/irdb-lib/pebliss/trunk/tests/test_imports/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_imports/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_imports/main.cpp b/irdb-lib/pebliss/trunk/tests/test_imports/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..242eb7c67835fd6cd5de70cd8d95ef90a73cc72c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_imports/main.cpp
@@ -0,0 +1,192 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void compare_imports(const imported_functions_list& imports, const imported_functions_list& new_imports, bool compare_original_iat = true)
+{
+	PE_TEST(imports.size() == new_imports.size(), "Import compare test (libraries)", test_level_critical);
+	for(size_t i = 0; i != imports.size(); ++i)
+	{
+		std::cout << "Library iteration = " << i << std::endl;
+		const import_library::imported_list& funcs = imports[i].get_imported_functions();
+		const import_library::imported_list& new_funcs = new_imports[i].get_imported_functions();
+
+		PE_TEST(imports[i].get_name() == new_imports[i].get_name()
+			&& imports[i].get_rva_to_iat() == new_imports[i].get_rva_to_iat()
+			&& imports[i].get_timestamp() == new_imports[i].get_timestamp(),
+			"Import compare test (library properties)", test_level_normal);
+
+		if(compare_original_iat)
+		{
+			PE_TEST(imports[i].get_rva_to_original_iat() == new_imports[i].get_rva_to_original_iat(), "Import compare test (library properties)", test_level_normal);
+		}
+
+		PE_TEST(funcs.size() == new_funcs.size(), "Import compare test (function count)", test_level_critical);
+		for(size_t j = 0; j != new_funcs.size(); ++j)
+		{
+			std::cout << "Function iteration = " << j << std::endl;
+			PE_TEST(funcs[i].has_name() == new_funcs[i].has_name(), "Import compare test (function properties)", test_level_normal);
+
+			if(compare_original_iat)
+			{
+				PE_TEST(funcs[i].get_iat_va() == new_funcs[i].get_iat_va(), "Import compare test (function properties)", test_level_normal);
+			}
+
+			if(funcs[i].has_name())
+			{
+				PE_TEST(funcs[i].get_name() == new_funcs[i].get_name() && funcs[i].get_hint() == new_funcs[i].get_hint(), "Import compare test (function properties)", test_level_normal);
+			}
+			else
+			{
+				PE_TEST(funcs[i].get_ordinal() == new_funcs[i].get_ordinal(), "Import compare test (function properties)", test_level_normal);
+			}
+		}
+	}
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	imported_functions_list imports;
+	PE_TEST_EXCEPTION(imports = get_imported_functions(image), "get_imported_functions test", test_level_critical);
+	PE_TEST(imports.size() == 2, "Imports test 1", test_level_normal);
+	PE_TEST(imports.at(0).get_name() == "USER32.dll", "Imports test 2", test_level_normal);
+	PE_TEST(imports.at(1).get_name() == "KERNEL32.dll", "Imports test 3", test_level_normal);
+
+	import_library& user32 = imports.at(0);
+	import_library& kernel32 = imports.at(1);
+
+	PE_TEST(user32.get_imported_functions().at(0).has_name() && user32.get_imported_functions().at(0).get_name() == "MessageBoxW", "Imports test 4", test_level_normal);
+	PE_TEST(kernel32.get_timestamp() == 0, "Imports test 5", test_level_normal);
+
+	if(image.get_pe_type() == pe_type_32)
+	{
+		PE_TEST(kernel32.get_rva_to_iat() == 0x00018000, "Imports test 6", test_level_normal);
+		PE_TEST(kernel32.get_rva_to_original_iat() == 0x0001CA20, "Imports test 7", test_level_normal);
+		PE_TEST(user32.get_imported_functions().at(0).get_hint() == 0x215, "Imports test 8", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(kernel32.get_rva_to_iat() == 0x0001B000, "Imports test 6", test_level_normal);
+		PE_TEST(kernel32.get_rva_to_original_iat() == 0x00022428, "Imports test 7", test_level_normal);
+		PE_TEST(user32.get_imported_functions().at(0).get_hint() == 0x219, "Imports test 8", test_level_normal);
+	}
+	
+	
+	imported_functions_list new_imports;
+
+	section s;
+	s.get_raw_data().resize(1);
+	section& import_section = image.add_section(s);
+
+	import_rebuilder_settings settings(true, false);
+	settings.build_original_iat(true);
+	settings.enable_auto_strip_last_section(true);
+	settings.fill_missing_original_iats(false);
+	settings.save_iat_and_original_iat_rvas(true, false);
+	settings.set_offset_from_section_start(0);
+
+	image_directory import_dir;
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 1", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 2", test_level_critical);
+	PE_TEST(import_dir.get_rva() == image.get_directory_rva(pe_win::image_directory_entry_import)
+		&& import_dir.get_size() == image.get_directory_size(pe_win::image_directory_entry_import), "Import directory test 1", test_level_critical);
+	PE_TEST(image.get_directory_rva(pe_win::image_directory_entry_iat) && image.get_directory_size(pe_win::image_directory_entry_iat), "Import directory test 2", test_level_critical);
+
+	compare_imports(imports, new_imports);
+
+	settings.zero_directory_entry_iat(true);
+	settings.set_offset_from_section_start(1);
+	import_section.get_raw_data() = "x";
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 2", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 3", test_level_critical);
+	PE_TEST(import_section.get_raw_data().substr(0, 1) == "x", "Import offset test 1", test_level_critical);
+	PE_TEST(!image.get_directory_rva(pe_win::image_directory_entry_iat) && !image.get_directory_size(pe_win::image_directory_entry_iat), "Import directory test 3", test_level_critical);
+	compare_imports(imports, new_imports);
+
+	settings.set_offset_from_section_start(10);
+	import_section.get_raw_data() = "0123456789";
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 3", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 4", test_level_critical);
+	PE_TEST(import_section.get_raw_data().substr(0, 10) == "0123456789", "Import offset test 2", test_level_critical);
+	compare_imports(imports, new_imports);
+
+	settings.save_iat_and_original_iat_rvas(true, true);
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 4", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 5", test_level_critical);
+	compare_imports(imports, new_imports);
+	
+	settings.build_original_iat(false);
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 5", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 6", test_level_critical);
+	PE_TEST(!new_imports[0].get_rva_to_original_iat() && !new_imports[1].get_rva_to_original_iat(), "Import original IAT test", test_level_normal);
+	compare_imports(imports, new_imports, false);
+	
+	settings.build_original_iat(true);
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 6", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 7", test_level_critical);
+	PE_TEST(new_imports[0].get_rva_to_original_iat() && new_imports[1].get_rva_to_original_iat(), "Import original IAT test 2", test_level_normal);
+	compare_imports(imports, new_imports, false);
+	
+	settings.fill_missing_original_iats(true);
+	settings.build_original_iat(false);
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 7", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 8", test_level_critical);
+	compare_imports(imports, new_imports, false);
+	
+	settings.save_iat_and_original_iat_rvas(false);
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, settings), "Import rebuilder test 8", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 9", test_level_critical);
+	PE_TEST(imports[0].get_rva_to_iat() != new_imports[0].get_rva_to_iat()
+		&& imports[1].get_rva_to_iat() != new_imports[1].get_rva_to_iat(), "IAT rebuilder test", test_level_normal);
+	
+
+	import_library lib;
+	lib.set_name("TEST.DLL");
+	lib.set_timestamp(0x12345);
+	imported_function func;
+	func.set_name("TestFunc");
+	func.set_iat_va(1);
+	lib.add_import(func);
+	func.set_name("AFunc");
+	lib.add_import(func);
+	
+	func.set_name("");
+	func.set_ordinal(123);
+	lib.add_import(func);
+
+	func.set_name("BFunc");
+	lib.add_import(func);
+
+	imports.push_back(lib);
+
+	import_rebuilder_settings new_settings;
+	new_settings.save_iat_and_original_iat_rvas(false);
+
+	PE_TEST_EXCEPTION(import_dir = rebuild_imports(image, imports, import_section, new_settings), "Import rebuilder test 9", test_level_critical);
+	PE_TEST_EXCEPTION(new_imports = get_imported_functions(image), "get_imported_functions test 10", test_level_critical);
+
+	PE_TEST(new_imports.size() == 3 && new_imports[2].get_name() == "TEST.DLL", "Added import test", test_level_normal);
+	PE_TEST(new_imports[2].get_imported_functions().size() == 4, "Added import function test 1", test_level_normal);
+	PE_TEST(new_imports[2].get_imported_functions()[1].get_name() == "AFunc", "Added import function test 2", test_level_normal);
+	PE_TEST(new_imports[2].get_imported_functions()[3].get_iat_va() == 1, "Added import function test 3", test_level_normal);
+	PE_TEST(new_imports[2].get_imported_functions()[2].has_name() == false, "Added import function test 4", test_level_normal);
+	PE_TEST(new_imports[2].get_imported_functions()[2].get_ordinal() == 123, "Added import function test 5", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcproj b/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..b701bb76369aa6b514bdd8f29efb8cc6b2e6a34f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_imports"
+	ProjectGUID="{BD969F96-E5A5-47B2-B5EF-B7999A441CE5}"
+	RootNamespace="test_imports"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcxproj b/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..b8793c39efca0c40470cf743a12d383500684561
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{CE1D0620-BC75-456F-914B-3BEBF5444B4C}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_imports</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_imports/test_imports.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_load_config/Makefile b/irdb-lib/pebliss/trunk/tests/test_load_config/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_load_config/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_load_config/main.cpp b/irdb-lib/pebliss/trunk/tests/test_load_config/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..eb62d59ba38a427120c772b96d0036f1f9bea23a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_load_config/main.cpp
@@ -0,0 +1,83 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void check_load_config(const image_config_info& info)
+{
+	PE_TEST(info.get_security_cookie_va() == 0x41E7F4, "Load Config Values test 1", test_level_normal);
+	PE_TEST(info.get_se_handler_count() == 0x20, "Load Config Values test 2", test_level_critical);
+	PE_TEST(info.get_time_stamp() == 0, "Load Config Values test 3", test_level_normal);
+	PE_TEST(info.get_se_handler_rvas()[1] == 0x731a, "Load Config Values test 4", test_level_normal);
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	if(image.get_pe_type() == pe_type_32)
+	{
+		image_config_info info;
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 1", test_level_critical);
+		check_load_config(info);
+
+		section s;
+		s.get_raw_data().resize(1);
+		s.set_name("newcfg");
+		section& new_config_section = image.add_section(s);
+
+		uint32_t old_dir_rva = image.get_directory_rva(pe_win::image_directory_entry_load_config);
+
+		PE_TEST_EXCEPTION(rebuild_image_config(image, info, new_config_section, 0, false, false, true, true), "Load Config Rebuilder test 1", test_level_critical);
+		PE_TEST(old_dir_rva != image.get_directory_rva(pe_win::image_directory_entry_load_config), "Load Config test 5", test_level_normal);
+
+		uint64_t old_se_handler_table_va = info.get_se_handler_table_va();
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 2", test_level_critical);
+		PE_TEST(old_se_handler_table_va == info.get_se_handler_table_va(), "Load Config test 5", test_level_normal);
+		check_load_config(info);
+
+		PE_TEST_EXCEPTION(rebuild_image_config(image, info, new_config_section, 0, true, false, true, true), "Load Config Rebuilder test 2", test_level_critical);
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 3", test_level_critical);
+		PE_TEST(old_se_handler_table_va != info.get_se_handler_table_va(), "Load Config test 6", test_level_normal);
+		check_load_config(info);
+
+		info.add_lock_prefix_rva(0x123);
+		info.add_lock_prefix_rva(0x456);
+		info.add_lock_prefix_rva(0x789);
+
+		PE_TEST_EXCEPTION(rebuild_image_config(image, info, new_config_section, 0, true, true, true, true), "Load Config Rebuilder test 3", test_level_critical);
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 4", test_level_critical);
+		check_load_config(info);
+		PE_TEST(info.get_lock_prefix_rvas().size() == 3, "Load Config Lock Prefix test 1", test_level_normal);
+		PE_TEST(info.get_lock_prefix_rvas()[2] == 0x789, "Load Config Lock Prefix test 2", test_level_normal);
+		
+		PE_TEST_EXCEPTION(rebuild_image_config(image, info, new_config_section, 1, true, true, true, true), "Load Config Rebuilder test 4", test_level_critical);
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 5", test_level_critical);
+		check_load_config(info);
+		PE_TEST_EXCEPTION(rebuild_image_config(image, info, new_config_section, 12, true, true, true, true), "Load Config Rebuilder test 5", test_level_critical);
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 6", test_level_critical);
+		check_load_config(info);
+
+		info.add_se_handler_rva(0x001); //Check sorting
+		info.set_lock_prefix_table_va(0);
+		PE_TEST_EXCEPTION(rebuild_image_config(image, info, new_config_section, 0, true, false, true, true), "Load Config Rebuilder test 5", test_level_critical);
+		PE_TEST_EXCEPTION(info = get_image_config(image), "Load Config Parser test 6", test_level_critical);
+		PE_TEST(info.get_se_handler_count() == 0x21, "Load Config Values test 5", test_level_critical);
+		PE_TEST(info.get_se_handler_rvas()[0] == 0x001, "Load Config Values test 6", test_level_normal); //Checks if list is sorted
+	}
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcproj b/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..e66c33ab9271bbb6fa40d123a2f1ab13a6327b1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_load_config"
+	ProjectGUID="{089E9482-33DD-4C64-84A1-C9B5F10F802A}"
+	RootNamespace="test_load_config"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcxproj b/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..5083d79429e7eebdc3bee24a0a4459d43420a511
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{FAD361E1-1FD7-4993-BD20-7450026E51CC}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_load_config</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_load_config/test_load_config.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_relocations/Makefile b/irdb-lib/pebliss/trunk/tests/test_relocations/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_relocations/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_relocations/main.cpp b/irdb-lib/pebliss/trunk/tests/test_relocations/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..12e166210f43cd373a6457deb58d6f163f939473
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_relocations/main.cpp
@@ -0,0 +1,100 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void test_relocations(const pe_base& image, const relocation_table_list& tables, bool read_absolute_entries)
+{
+	if(image.get_pe_type() == pe_type_32)
+	{
+		PE_TEST(tables.size() == 30, "Relocation test 1", test_level_critical);
+		PE_TEST(tables[1].get_rva() == 0x2000, "Relocation test 2", test_level_normal);
+		PE_TEST(tables[1].get_relocations().size() == (read_absolute_entries ? 22 : 21), "Relocation test 3", test_level_critical);
+		PE_TEST(tables[1].get_relocations()[1].get_rva() == 0x54, "Relocation test 4", test_level_normal);
+		PE_TEST(tables[1].get_relocations()[1].get_type() == pe_win::image_rel_based_highlow, "Relocation test 5", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(tables.size() == 7, "Relocation test 1", test_level_critical);
+		PE_TEST(tables[1].get_rva() == 0x1C000, "Relocation test 2", test_level_normal);
+		PE_TEST(tables[4].get_relocations().size() == (read_absolute_entries ? 6 : 5), "Relocation test 3", test_level_critical);
+		PE_TEST(tables[1].get_relocations()[1].get_rva() == 0x4E8, "Relocation test 4", test_level_normal);
+		PE_TEST(tables[1].get_relocations()[1].get_type() == pe_win::image_rel_based_dir64, "Relocation test 5", test_level_normal);
+	}
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	relocation_table_list tables;
+	PE_TEST_EXCEPTION(tables = get_relocations(image, true), "Relocation parser test 1", test_level_critical);
+	test_relocations(image, tables, true);
+	
+	tables.clear();
+	PE_TEST_EXCEPTION(tables = get_relocations(image, false), "Relocation parser test 2", test_level_critical);
+	test_relocations(image, tables, false);
+
+	section& reloc_section = image.section_from_directory(pe_win::image_directory_entry_basereloc);
+	PE_TEST_EXCEPTION(rebuild_relocations(image, tables, reloc_section, 0, true, true), "Relocation Rebuilder test 1", test_level_critical);
+	PE_TEST_EXCEPTION(tables = get_relocations(image, true), "Relocation parser test 3", test_level_critical);
+	test_relocations(image, tables, true);
+
+	PE_TEST_EXCEPTION(rebuild_relocations(image, tables, reloc_section, 0, true, true), "Relocation Rebuilder test 2", test_level_critical);
+	PE_TEST_EXCEPTION(tables = get_relocations(image, true), "Relocation parser test 4", test_level_critical);
+	test_relocations(image, tables, true);
+
+	section s;
+	s.get_raw_data().resize(1);
+	s.set_name("newreloc");
+	section& new_reloc_section = image.add_section(s);
+
+	uint32_t old_reloc_rva = image.get_directory_rva(pe_win::image_directory_entry_basereloc);
+
+	PE_TEST_EXCEPTION(rebuild_relocations(image, tables, new_reloc_section, 0, true, true), "Relocation Rebuilder test 3", test_level_critical);
+	PE_TEST(old_reloc_rva != image.get_directory_rva(pe_win::image_directory_entry_basereloc), "Relocation Rebuilder test 4", test_level_normal);
+	
+	old_reloc_rva = image.get_directory_rva(pe_win::image_directory_entry_basereloc);
+
+	PE_TEST_EXCEPTION(tables = get_relocations(image, false), "Relocation parser test 5", test_level_critical);
+	test_relocations(image, tables, false);
+	
+	new_reloc_section.set_raw_data("111");
+	PE_TEST_EXCEPTION(rebuild_relocations(image, tables, new_reloc_section, 3, true, true), "Relocation Rebuilder test 4", test_level_critical);
+	PE_TEST(new_reloc_section.get_raw_data().substr(0, 3) == "111", "Relocation Rebuilder offset test", test_level_normal);
+	PE_TEST(old_reloc_rva != image.get_directory_rva(pe_win::image_directory_entry_basereloc), "Relocation Rebuilder test 5", test_level_normal);
+	
+	PE_TEST_EXCEPTION(tables = get_relocations(image, false), "Relocation parser test 6", test_level_critical);
+	test_relocations(image, tables, false);
+
+	relocation_table_list full_tables; //With absolute entries
+	PE_TEST_EXCEPTION(full_tables = get_relocations(image, true), "Relocation parser test 7", test_level_critical);
+	test_relocations(image, full_tables, true);
+	
+	pe_base old_image(image);
+
+	PE_TEST_EXCEPTION(rebase_image(image, tables, image.get_image_base_64() + 0x10000), "PE Rebaser test 1", test_level_critical);
+	PE_TEST_EXCEPTION(rebase_image(image, full_tables, image.get_image_base_64() - 0x10000), "PE Rebaser test 2", test_level_critical); //Check that rebaser skips absolute entries
+
+	uint16_t section_count = image.get_number_of_sections();
+	for(uint16_t i = 0; i != section_count; ++i)
+	{
+		std::cout << "Rebaser control test iteration: " << i << std::endl;
+		PE_TEST(image.get_image_sections().at(i).get_raw_data() == old_image.get_image_sections().at(i).get_raw_data(), "Rebaser control test", test_level_normal);
+	}
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcproj b/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..8256125da44c2088c0c89f37256381bcb7e2cd70
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_relocations"
+	ProjectGUID="{997A89F0-372D-4306-AE4D-7438D93273C3}"
+	RootNamespace="test_relocations"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcxproj b/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..83fbafdfc54bb9fb8678dd2758a7228564ba3309
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{709B0E41-9792-4A0A-B28B-CBD06CE441B9}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_relocations</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..12409d248c06566328fc21348384c0e1e43e7cd9
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_relocations/test_relocations.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1640bfd45c4521c7a1dc43607c5b4eb7b4202751
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/main.cpp
@@ -0,0 +1,59 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root(get_resources(image));
+	
+	pe_resource_manager res(root);
+	resource_bitmap_reader bmp_read(res);
+	resource_bitmap_writer bmp_write(res);
+	
+	PE_TEST_EXPECT_EXCEPTION(bmp_read.get_bitmap_by_name(L"TEST"), pe_exception::resource_directory_entry_not_found, "Bitmap Reader test 1", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(bmp_read.get_bitmap_by_name(123, L"TEST"), pe_exception::resource_directory_entry_not_found, "Bitmap Reader test 2", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(bmp_read.get_bitmap_by_id(123), pe_exception::resource_directory_entry_not_found, "Bitmap Reader test 3", test_level_normal);
+
+	std::string bitmap;
+	PE_TEST_EXCEPTION(bitmap = bmp_read.get_bitmap_by_id(102), "Bitmap Reader test 4", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(bmp_read.get_bitmap_by_id(102, 1), pe_exception::resource_data_entry_not_found, "Bitmap Reader test 5", test_level_normal);
+	PE_TEST_EXCEPTION(bmp_write.add_bitmap(bitmap, L"TEST", 1049, 1234, 5678), "Bitmap Writer test 1", test_level_normal);
+	
+	std::string bitmap2;
+	PE_TEST_EXCEPTION(bitmap2 = bmp_read.get_bitmap_by_name(1049, L"TEST"), "Bitmap Reader test 6", test_level_critical);
+	PE_TEST(bitmap == bitmap2, "Bitmap Reader test 7", test_level_normal);
+	
+	PE_TEST_EXCEPTION(bmp_write.add_bitmap(bitmap, 9000, 1049, 1234, 5678), "Bitmap Writer test 2", test_level_critical);
+	PE_TEST_EXCEPTION(bitmap2 = bmp_read.get_bitmap_by_id(9000), "Bitmap Reader test 8", test_level_normal);
+	PE_TEST(bitmap == bitmap2, "Bitmap Reader test 9", test_level_normal);
+	
+	PE_TEST_EXCEPTION(bitmap = bmp_read.get_bitmap_by_id(103), "Bitmap Reader test 10", test_level_normal);
+	PE_TEST_EXCEPTION(bmp_write.add_bitmap(bitmap, 9000, 1049, 1234, 5678), "Bitmap Writer test 3 (bitmap replace test)", test_level_critical);
+	PE_TEST_EXCEPTION(bitmap2 = bmp_read.get_bitmap_by_id(9000), "Bitmap Reader test 11", test_level_normal);
+	PE_TEST(bitmap == bitmap2, "Bitmap Reader test 12", test_level_normal);
+	
+	PE_TEST_EXCEPTION(bmp_write.remove_bitmap(9000, 1049), "Bitmap Writer test 4", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(bmp_read.get_bitmap_by_id(9000), pe_exception::resource_directory_entry_not_found, "Bitmap Reader test 13", test_level_normal);
+
+	PE_TEST_EXCEPTION(bmp_write.remove_bitmap(L"TEST", 1049), "Bitmap Writer test 5", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(bmp_read.get_bitmap_by_name(L"TEST"), pe_exception::resource_directory_entry_not_found, "Bitmap Reader test 14", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..ffb4ba74866c76c5209b436e98b704661859376e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_bitmap"
+	ProjectGUID="{1B337DC2-628E-4DA4-8C0F-A6880289C6E2}"
+	RootNamespace="test_resource_bitmap"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..85f748a41507f5bd3a80ff6ee2418b02172b639b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcxproj
@@ -0,0 +1,168 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{F401B9A2-B8CB-477A-A515-F029D0AA5553}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_bitmap_reader</RootNamespace>
+    <ProjectName>test_resource_bitmap</ProjectName>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_bitmap/test_resource_bitmap.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..0e373e66fb30a5ebd85f699b6b0c62dd1455d824
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/main.cpp
@@ -0,0 +1,120 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root(get_resources(image));
+	
+	pe_resource_manager res(root);
+	resource_cursor_icon_reader ico_read(res);
+	resource_cursor_icon_writer ico_write(res);
+	
+	std::string icon, icon2;
+
+	//Named icon groups tests
+	PE_TEST_EXCEPTION(icon = ico_read.get_single_icon_by_id(5), "Icon Reader test 1", test_level_normal);
+	PE_TEST_EXCEPTION(ico_write.add_icon(icon, L"NEW_GROUP", 1033, resource_cursor_icon_writer::icon_place_free_ids, 1234, 5678), "Icon Writer test 1", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_icon_by_name(1033, L"NEW_GROUP"), "Icon Reader test 2", test_level_normal); //This group contains single icon
+	PE_TEST(icon == icon2, "Icon Reader test 3", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_icon_by_id(1), "Icon Reader test 4", test_level_normal); //icon_place_free_ids - the first free id was 1
+
+	PE_TEST_EXCEPTION(ico_write.remove_icon_group(L"NEW_GROUP", 1033), "Icon Writer test 2", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_icon_by_name(1033, L"NEW_GROUP"), pe_exception::resource_directory_entry_not_found, "Icon Reader test 5", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_single_icon_by_id(1), pe_exception::resource_directory_entry_not_found, "Icon Reader test 6", test_level_normal);
+
+	PE_TEST_EXCEPTION(icon = ico_read.get_icon_by_name(1049, L"MAIN_ICON"), "Icon Reader test 7", test_level_normal);
+	
+	PE_TEST_EXCEPTION(ico_write.add_icon(icon, L"NEW_GROUP", 1033, resource_cursor_icon_writer::icon_place_after_max_icon_id, 1234, 5678), "Icon Writer test 3", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_icon_by_name(1033, L"NEW_GROUP"), "Icon Reader test 8", test_level_normal); //This group contains single icon
+	PE_TEST(icon == icon2, "Icon Reader test 9", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_icon_by_id(18), "Icon Reader test 10", test_level_normal); //icon_place_after_max_icon_id - the last free id was 17, and MAIN_ICON contains more than one icon
+	PE_TEST_EXCEPTION(ico_read.get_single_icon_by_id(19), "Icon Reader test 11", test_level_normal);
+
+	PE_TEST_EXCEPTION(ico_write.remove_icon_group(L"NEW_GROUP", 1033), "Icon Writer test 4", test_level_critical);
+
+
+	//ID icon groups tests
+	PE_TEST_EXCEPTION(icon = ico_read.get_single_icon_by_id(5), "Icon Reader test 12", test_level_normal);
+	PE_TEST_EXCEPTION(ico_write.add_icon(icon, 777, 1033, resource_cursor_icon_writer::icon_place_free_ids, 1234, 5678), "Icon Writer test 5", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_icon_by_id_lang(1033, 777), "Icon Reader test 13", test_level_normal); //This group contains single icon
+	PE_TEST(icon == icon2, "Icon Reader test 14", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_icon_by_id(1), "Icon Reader test 15", test_level_normal); //icon_place_free_ids - the first free id was 1
+
+	PE_TEST_EXCEPTION(ico_write.remove_icon_group(777, 1033), "Icon Writer test 6", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_icon_by_id_lang(1033, 777), pe_exception::resource_directory_entry_not_found, "Icon Reader test 16", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_single_icon_by_id(1), pe_exception::resource_directory_entry_not_found, "Icon Reader test 17", test_level_normal);
+
+	PE_TEST_EXCEPTION(icon = ico_read.get_icon_by_name(1049, L"MAIN_ICON"), "Icon Reader test 18", test_level_normal);
+	
+	PE_TEST_EXCEPTION(ico_write.add_icon(icon, 777, 1033, resource_cursor_icon_writer::icon_place_after_max_icon_id, 1234, 5678), "Icon Writer test 7", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_icon_by_id_lang(1033, 777), "Icon Reader test 19", test_level_normal); //This group contains single icon
+	PE_TEST(icon == icon2, "Icon Reader test 20", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_icon_by_id(18), "Icon Reader test 21", test_level_normal); //icon_place_after_max_icon_id - the last free id was 17, and MAIN_ICON contains more than one icon
+	PE_TEST_EXCEPTION(ico_read.get_single_icon_by_id(19), "Icon Reader test 22", test_level_normal);
+
+	PE_TEST_EXCEPTION(ico_write.remove_icon_group(777, 1033), "Icon Writer test 8", test_level_critical);
+
+
+	//Named cursor groups tests
+	PE_TEST_EXCEPTION(icon = ico_read.get_single_cursor_by_id(3), "Cursor Reader test 1", test_level_normal);
+	PE_TEST_EXCEPTION(ico_write.add_cursor(icon, L"NEW_GROUP", 1033, resource_cursor_icon_writer::icon_place_free_ids, 1234, 5678), "Cursor Writer test 1", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_cursor_by_name(1033, L"NEW_GROUP"), "Cursor Reader test 2", test_level_normal); //This group contains single cursor
+	PE_TEST(icon == icon2, "Cursor Reader test 3", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_cursor_by_id(4), "Cursor Reader test 4", test_level_normal); //icon_place_free_ids - the first free id was 4
+
+	PE_TEST_EXCEPTION(ico_write.remove_cursor_group(L"NEW_GROUP", 1033), "Cursor Writer test 2", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_cursor_by_name(1033, L"NEW_GROUP"), pe_exception::resource_directory_entry_not_found, "Cursor Reader test 5", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_single_cursor_by_id(4), pe_exception::resource_directory_entry_not_found, "Cursor Reader test 6", test_level_normal);
+
+	PE_TEST_EXCEPTION(icon = ico_read.get_cursor_by_id_lang(1049, 105), "Cursor Reader test 7", test_level_normal);
+	
+	PE_TEST_EXCEPTION(ico_write.add_cursor(icon, L"NEW_GROUP", 1033, resource_cursor_icon_writer::icon_place_after_max_icon_id, 1234, 5678), "Cursor Writer test 3", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_cursor_by_name(1033, L"NEW_GROUP"), "Cursor Reader test 8", test_level_normal); //This group contains single cursor
+	PE_TEST(icon == icon2, "Cursor Reader test 9", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_cursor_by_id(4), "Cursor Reader test 10", test_level_normal); //icon_place_after_max_icon_id - the last free id was 4, and cursor group "105" contains more than one cursor
+	PE_TEST_EXCEPTION(ico_read.get_single_cursor_by_id(5), "Cursor Reader test 11", test_level_normal);
+
+	PE_TEST_EXCEPTION(ico_write.remove_cursor_group(L"NEW_GROUP", 1033), "Cursor Writer test 4", test_level_critical);
+
+
+	//ID cursor groups tests
+	PE_TEST_EXCEPTION(icon = ico_read.get_single_cursor_by_id(3), "Cursor Reader test 12", test_level_normal);
+	PE_TEST_EXCEPTION(ico_write.add_cursor(icon, 777, 1033, resource_cursor_icon_writer::icon_place_free_ids, 1234, 5678), "Cursor Writer test 5", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_cursor_by_id_lang(1033, 777), "Cursor Reader test 13", test_level_normal); //This group contains single cursor
+	PE_TEST(icon == icon2, "Cursor Reader test 14", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_cursor_by_id(4), "Cursor Reader test 15", test_level_normal); //icon_place_free_ids - the first free id was 4
+
+	PE_TEST_EXCEPTION(ico_write.remove_cursor_group(777, 1033), "Cursor Writer test 6", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_cursor_by_id_lang(1033, 777), pe_exception::resource_directory_entry_not_found, "Cursor Reader test 16", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ico_read.get_single_cursor_by_id(4), pe_exception::resource_directory_entry_not_found, "Cursor Reader test 17", test_level_normal);
+
+	PE_TEST_EXCEPTION(icon = ico_read.get_cursor_by_id_lang(1049, 105), "Cursor Reader test 18", test_level_normal);
+	
+	PE_TEST_EXCEPTION(ico_write.add_cursor(icon, 777, 1033, resource_cursor_icon_writer::icon_place_after_max_icon_id, 1234, 5678), "Cursor Writer test 7", test_level_critical);
+	PE_TEST_EXCEPTION(icon2 = ico_read.get_cursor_by_id_lang(1033, 777), "Cursor Reader test 19", test_level_normal); //This group contains single cursor
+	PE_TEST(icon == icon2, "Cursor Reader test 20", test_level_normal);
+	PE_TEST_EXCEPTION(ico_read.get_single_cursor_by_id(4), "Cursor Reader test 21", test_level_normal); //icon_place_after_max_icon_id - the last free id was 4, and cursor group "105" contains more than one cursor
+	PE_TEST_EXCEPTION(ico_read.get_single_cursor_by_id(5), "Cursor Reader test 22", test_level_normal);
+
+	PE_TEST_EXCEPTION(ico_write.remove_cursor_group(777, 1033), "Cursor Writer test 8", test_level_critical);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..217078c56a1894244bc20aa9eb830e5c3ca5d170
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_icon_cursor"
+	ProjectGUID="{1E59538C-2C78-4D35-8639-568890543A4A}"
+	RootNamespace="test_resource_icon_cursor"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..bd7fbead1d50a9f209feffeee37ef0713a26606a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{D9AC6F2E-3FE9-4D64-BEAA-C7104A0397B2}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resource_icon_cursor</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_icon_cursor/test_resource_icon_cursor.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_manager/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_manager/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_manager/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_manager/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_manager/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..c69b45c481073cabfa10cc3cee10c07285362a67
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_manager/main.cpp
@@ -0,0 +1,68 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root(get_resources(image));
+
+	pe_resource_manager res(root);
+
+	PE_TEST(res.remove_resource_type(pe_resource_viewer::resource_bitmap) == true, "Resource Manager test 1", test_level_normal);
+	PE_TEST(res.remove_resource_type(pe_resource_viewer::resource_bitmap) == false, "Resource Manager test 2", test_level_normal);
+	PE_TEST(res.remove_resource(L"DOESNOT_EXIST") == false, "Resource Manager test 3", test_level_normal);
+	
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_icon_group, 107) == true, "Resource Manager test 4", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_icon_group, 107) == false, "Resource Manager test 5", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_icon_group, L"MAIN_ICON") == true, "Resource Manager test 6", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_icon_group, L"MAIN_ICON") == false, "Resource Manager test 7", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_bitmap, 101) == false, "Resource Manager test 8", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_bitmap, L"TEST") == false, "Resource Manager test 9", test_level_normal);
+	PE_TEST(res.remove_resource(L"TEST", 1) == false, "Resource Manager test 10", test_level_normal);
+	PE_TEST(res.remove_resource(L"TEST", L"TEST") == false, "Resource Manager test 11", test_level_normal);
+	
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_cursor_group, 104, 1047) == false, "Resource Manager test 12", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_cursor_group, 104, 1049) == true, "Resource Manager test 13", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_cursor_group, 104, 1049) == false, "Resource Manager test 14", test_level_normal);
+	PE_TEST(res.remove_resource(L"TEST", 100, 1049) == false, "Resource Manager test 15", test_level_normal);
+	PE_TEST(res.remove_resource(L"TEST", L"TEST", 1049) == false, "Resource Manager test 16", test_level_normal);
+	PE_TEST(res.remove_resource(pe_resource_viewer::resource_cursor_group, L"TEST", 1049) == false, "Resource Manager test 17", test_level_normal);
+
+	PE_TEST_EXCEPTION(res.add_resource("res data", pe_resource_viewer::resource_rcdata, L"TESTNAME", 1049, 123, 12345), "Resource Manager test 18", test_level_normal);
+	PE_TEST(res.get_resource_data_by_name(1049, pe_resource_viewer::resource_rcdata, L"TESTNAME").get_data() == "res data", "Resource Manager test 19", test_level_normal);
+	PE_TEST(res.get_resource_data_by_name(1049, pe_resource_viewer::resource_rcdata, L"TESTNAME").get_codepage() == 123, "Resource Manager test 20", test_level_normal);
+
+	PE_TEST_EXCEPTION(res.add_resource("res data 2", L"ROOT", L"TESTNAME", 1049, 456, 12345), "Resource Manager test 21", test_level_normal);
+	PE_TEST(res.get_resource_data_by_name(1049, L"ROOT", L"TESTNAME").get_data() == "res data 2", "Resource Manager test 22", test_level_normal);
+	PE_TEST(res.get_resource_data_by_name(1049, L"ROOT", L"TESTNAME").get_codepage() == 456, "Resource Manager test 23", test_level_normal);
+
+	PE_TEST_EXCEPTION(res.add_resource("res data", pe_resource_viewer::resource_rcdata, 12345, 1049, 123, 12345), "Resource Manager test 24", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(1049, pe_resource_viewer::resource_rcdata, 12345).get_data() == "res data", "Resource Manager test 25", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(1049, pe_resource_viewer::resource_rcdata, 12345).get_codepage() == 123, "Resource Manager test 26", test_level_normal);
+
+	PE_TEST_EXCEPTION(res.add_resource("res data 2", L"ROOT", 12345, 1049, 456, 12345), "Resource Manager test 27", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(1049, L"ROOT", 12345).get_data() == "res data 2", "Resource Manager test 28", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(1049, L"ROOT", 12345).get_codepage() == 456, "Resource Manager test 29", test_level_normal);
+
+	PE_TEST_EXCEPTION(res.add_resource("res data 3", L"ROOT", 12345, 1049, 456, 12345), "Resource Manager test 30", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(1049, L"ROOT", 12345).get_data() == "res data 3", "Resource Manager test 31", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..9dc242cbf0aa8d4a59460d940cb28074723ac739
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_manager"
+	ProjectGUID="{39E1826B-5436-47D3-9B95-D3C667691461}"
+	RootNamespace="test_resource_manager"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..b41c9f6fb5effa780d3a204c1cbe824803619f54
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{415A9FD5-59F6-4B1B-8EB8-EBD87E37EEA4}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resource_manager</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_manager/test_resource_manager.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_message_table/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_message_table/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..60d598820b42710837d23ea70f04d4c7f1ce6bd5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/main.cpp
@@ -0,0 +1,62 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root(get_resources(image));
+
+	pe_resource_manager res(root);
+	resource_message_list_reader msg(res);
+
+	resource_message_list messages;
+
+	//Unicode tests
+	PE_TEST_EXCEPTION(messages = msg.get_message_table_by_id_lang(1049, 1), "Message Table Parser test 1", test_level_critical);
+	PE_TEST(messages.size() == 2, "Message Table Parser test 2", test_level_critical);
+	PE_TEST(messages.find(0x01000000) != messages.end()
+		&& messages.find(0xC1000001) != messages.end(), "Message Table Parser test 3", test_level_critical);
+	PE_TEST(messages[0xC1000001].is_unicode(), "Message Table Parser test 4", test_level_normal);
+	PE_TEST(messages[0xC1000001].get_unicode_string() == L"Ошибка!\r\n", "Message Table Parser test 5", test_level_normal);
+
+	PE_TEST_EXCEPTION(messages = msg.get_message_table_by_id_lang(1033, 1), "Message Table Parser test 6", test_level_critical);
+	PE_TEST(messages.size() == 2, "Message Table Parser test 7", test_level_critical);
+	PE_TEST(messages.find(0x01000000) != messages.end()
+		&& messages.find(0xC1000001) != messages.end(), "Message Table Parser test 8", test_level_critical);
+	PE_TEST(messages[0xC1000001].is_unicode(), "Message Table Parser test 9", test_level_normal);
+	PE_TEST(messages[0xC1000001].get_unicode_string() == L"Error!\r\n", "Message Table Parser test 10", test_level_normal);
+
+	//ANSI Tests
+	PE_TEST_EXCEPTION(messages = msg.get_message_table_by_id_lang(1049, 2), "Message Table Parser test 11", test_level_critical);
+	PE_TEST(messages.size() == 2, "Message Table Parser test 12", test_level_critical);
+	PE_TEST(messages.find(0x01000000) != messages.end()
+		&& messages.find(0xC1000001) != messages.end(), "Message Table Parser test 13", test_level_critical);
+	PE_TEST(!messages[0xC1000001].is_unicode(), "Message Table Parser test 14", test_level_normal);
+	PE_TEST(messages[0xC1000001].get_ansi_string() == "\xCE\xF8\xE8\xE1\xEA\xE0!\r\n", "Message Table Parser test 15", test_level_normal); //"Ошибка!\r\n"
+
+	PE_TEST_EXCEPTION(messages = msg.get_message_table_by_id_lang(1033, 2), "Message Table Parser test 16", test_level_critical);
+	PE_TEST(messages.size() == 2, "Message Table Parser test 17", test_level_critical);
+	PE_TEST(messages.find(0x01000000) != messages.end()
+		&& messages.find(0xC1000001) != messages.end(), "Message Table Parser test 18", test_level_critical);
+	PE_TEST(!messages[0xC1000001].is_unicode(), "Message Table Parser test 19", test_level_normal);
+	PE_TEST(messages[0xC1000001].get_ansi_string() == "Error!\r\n", "Message Table Parser test 20", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..deb049798a35b072f235fb2655b9b375ff01f544
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_message_table"
+	ProjectGUID="{57EFEFC9-E2D9-418E-9F05-3FD0D9921251}"
+	RootNamespace="test_resource_message_table"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..5edc5ca5ebc6e0d7e3bca4352151e5331935cc37
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{6CBACE55-8DDC-4EAE-A23A-DF412265D30C}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resource_message_table</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_message_table/test_resource_message_table.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_string_table/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_string_table/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..72e54de944c963841eaeb044320be6caee392559
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/main.cpp
@@ -0,0 +1,41 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root(get_resources(image));
+	
+	pe_resource_manager res(root);
+	resource_string_table_reader str(res);
+
+	resource_string_list strings;
+	PE_TEST_EXCEPTION(strings = str.get_string_table_by_id_lang(1049, 7), "String List Parser test 1", test_level_critical);
+	PE_TEST(strings.size() == 4, "String List Parser test 2", test_level_critical);
+	PE_TEST(strings.find(111) != strings.end(), "String List Parser test 3", test_level_critical);
+	PE_TEST(strings[111] == L"Test String 4", "String List Parser test 4", test_level_normal);
+
+	std::wstring str_111;
+	PE_TEST_EXCEPTION(str_111 = str.get_string_by_id(111), "String List Parser test 5", test_level_normal);
+	PE_TEST(str_111 == L"Test String 4", "String List Parser test 6", test_level_normal);
+	PE_TEST(str_111 == str.get_string_by_id_lang(1049, 111), "String List Parser test 7", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..bab4cc87ab7a7e49325d6a20fa3d416a7a6c2754
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_string_table"
+	ProjectGUID="{C68A466D-0C1B-40BC-9AB1-49B582958524}"
+	RootNamespace="test_resource_string_table"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..5973303e806a0b2fa1b7c51feb9453b46668b993
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{5E32A144-2F2D-4BB1-BBEF-13BE94414E99}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resource_string_table</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_string_table/test_resource_string_table.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_version_info/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_version_info/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..24757f90a52c21b02a49b6131e6590a362e3c4b6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/main.cpp
@@ -0,0 +1,97 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void test_version(const resource_version_info_reader& ver_reader, file_version_info& file_info, lang_string_values_map& strings, translation_values_map& translations)
+{
+	strings.clear();
+	translations.clear();
+
+	PE_TEST_EXCEPTION(file_info = ver_reader.get_version_info(strings, translations), "Version Info Parser test 1", test_level_critical);
+	PE_TEST(strings.size() == 2 && translations.size() == 2, "Version Info Parser test 2", test_level_critical);
+	PE_TEST(strings.find(L"040004b0") != strings.end() && strings.find(L"041904b0") != strings.end(), "Version Info Parser test 3", test_level_critical);
+	PE_TEST(translations.find(0x0400) != translations.end() && translations.find(0x0419) != translations.end(), "Version Info Parser test 4", test_level_critical);
+	PE_TEST(strings[L"040004b0"][L"FileDescription"] == L"PE Bliss Test PE File", "Version Info Parser test 5", test_level_normal);
+	PE_TEST(strings[L"041904b0"][L"FileDescription"] == L"PE Bliss - Тестовый PE-файл", "Version Info Parser test 6", test_level_normal);
+	PE_TEST((*translations.find(0x0400)).second == 0x4b0 && (*translations.find(0x0419)).second == 0x4b0, "Version Info Parser test 7", test_level_normal);
+	PE_TEST(file_info.get_file_date_ls() == 0 && file_info.get_file_date_ms() == 0
+		&& file_info.get_file_flags() == 0 && file_info.get_file_os() == file_version_info::file_os_nt_win32
+		&& file_info.get_file_subtype() == 0 && file_info.get_file_type() == file_version_info::file_type_application
+		&& file_info.get_file_version_ls() == 0x00020001 && file_info.get_file_version_ms() == 0x00040003
+		&& file_info.get_product_version_ls() == 0x00070008 && file_info.get_product_version_ms() == 0x00050006
+		&& file_info.get_file_version_string<char>() == "4.3.2.1"
+		&& file_info.get_product_version_string<wchar_t>() == L"5.6.7.8", "File Version Info Parser test", test_level_normal);
+
+	version_info_viewer ver_view(strings, translations);
+	version_info_editor ver_edit(strings, translations);
+
+	PE_TEST(version_info_viewer::translation_from_string(L"041904b0").first == 0x0419
+		&& version_info_viewer::translation_from_string(L"041904b0").second == 0x04b0, "translation_from_string test", test_level_normal);
+
+	PE_TEST(ver_view.get_company_name() == L"PE Bliss", "Version Info Viewer test 1", test_level_normal);
+	PE_TEST(ver_view.get_company_name(L"040004b0") == L"PE Bliss", "Version Info Viewer test 2", test_level_normal);
+	PE_TEST(ver_view.get_file_description() == L"PE Bliss - Тестовый PE-файл", "Version Info Viewer test 3", test_level_normal);
+	PE_TEST(ver_view.get_file_description(L"040004b0") == L"PE Bliss Test PE File", "Version Info Viewer test 4", test_level_normal);
+	PE_TEST(ver_view.get_file_version() == L"4.3.2.1", "Version Info Viewer test 5", test_level_normal);
+	PE_TEST(ver_view.get_file_version(L"040004b0") == L"4.3.2.1", "Version Info Viewer test 6", test_level_normal);
+	PE_TEST(ver_view.get_internal_name() == L"test.exe", "Version Info Viewer test 7", test_level_normal);
+	PE_TEST(ver_view.get_internal_name(L"040004b0") == L"test.exe", "Version Info Viewer test 8", test_level_normal);
+	PE_TEST(ver_view.get_legal_copyright() == L"(C) dx", "Version Info Viewer test 9", test_level_normal);
+	PE_TEST(ver_view.get_legal_copyright(L"040004b0") == L"(C) dx", "Version Info Viewer test 10", test_level_normal);
+	PE_TEST(ver_view.get_original_filename() == L"original.exe", "Version Info Viewer test 11", test_level_normal);
+	PE_TEST(ver_view.get_original_filename(L"040004b0") == L"original.exe", "Version Info Viewer test 12", test_level_normal);
+	PE_TEST(ver_view.get_product_name() == L"PE Bliss - Тесты", "Version Info Viewer test 13", test_level_normal);
+	PE_TEST(ver_view.get_product_name(L"040004b0") == L"PE Bliss Test", "Version Info Viewer test 14", test_level_normal);
+	PE_TEST(ver_view.get_product_version() == L"5.6.7.8", "Version Info Viewer test 15", test_level_normal);
+	PE_TEST(ver_view.get_product_version(L"040004b0") == L"5.6.7.8", "Version Info Viewer test 16", test_level_normal);
+	PE_TEST(ver_view.get_property(L"CompanyName", L"", false) == L"PE Bliss", "Version Info Viewer test 17", test_level_normal);
+	PE_TEST(ver_view.get_property(L"CompanyName", L"040004b0", false) == L"PE Bliss", "Version Info Viewer test 18", test_level_normal);
+	PE_TEST(ver_view.get_property(L"TestProperty", L"", false) == L"", "Version Info Viewer test 19", test_level_normal);
+	PE_TEST(ver_view.get_property(L"TestProperty", L"040004b0", false) == L"", "Version Info Viewer test 20", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ver_view.get_property(L"TestProperty", L"", true) == L"", pe_exception::version_info_string_does_not_exist, "Version Info Viewer test 21", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ver_view.get_property(L"TestProperty", L"040004b0", true) == L"", pe_exception::version_info_string_does_not_exist, "Version Info Viewer test 22", test_level_normal);
+	PE_TEST(ver_view.get_translation_list().size() == 2, "Version Info Viewer test 23", test_level_critical);
+	PE_TEST(ver_view.get_translation_list().at(1) == L"041904b0", "Version Info Viewer test 24", test_level_critical);
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+
+	resource_directory root(get_resources(image));
+
+	pe_resource_manager res(root);
+	resource_version_info_reader ver_reader(res);
+	resource_version_info_writer ver_writer(res);
+
+	file_version_info file_info;
+	lang_string_values_map strings;
+	translation_values_map translations;
+	test_version(ver_reader, file_info, strings, translations);
+
+	PE_TEST(ver_writer.remove_version_info(1049) == true, "Version Info Writer test 1", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(ver_reader.get_version_info(strings, translations), pe_exception::resource_directory_entry_not_found, "Version Info Parser test", test_level_critical);
+
+	PE_TEST_EXCEPTION(ver_writer.set_version_info(file_info, strings, translations, 12345, 678, 123), "Version Info Writer test 2", test_level_critical);
+	test_version(ver_reader, file_info, strings, translations);
+	
+	
+	
+	
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..9f043e4d185140d40f07aa4539244ee315ff14c5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_version_info"
+	ProjectGUID="{C30B270A-4C93-44A3-AABE-633713D0F1D7}"
+	RootNamespace="test_resource_version_info"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..a8415847759f9271d1c17db2eb32377c305fbd65
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{5C2B081E-5414-437B-86EB-B2695AEDF3F0}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resource_version_info</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_version_info/test_resource_version_info.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_viewer/Makefile b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_viewer/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..510313e8ea59cc6fd774e57de2bde70bca69a8fd
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/main.cpp
@@ -0,0 +1,89 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root(get_resources(image));
+
+	pe_resource_viewer res(root);
+
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_count(L"NoName") == 0, pe_exception::resource_directory_entry_not_found, "Resource viewer test 1", test_level_normal);
+	PE_TEST(res.get_resource_count(pe_resource_viewer::resource_cursor) == 3, "Resource viewer test 2", test_level_normal);
+	
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(L"NoName", 123) == 0, pe_exception::resource_directory_entry_not_found, "Resource viewer test 3", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(pe_resource_viewer::resource_accelerator, 123), pe_exception::resource_directory_entry_not_found, "Resource viewer test 4", test_level_normal);
+	
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(pe_resource_viewer::resource_cursor, 5) == 0, pe_exception::resource_directory_entry_not_found, "Resource viewer test 5", test_level_normal);
+	PE_TEST(res.get_language_count(pe_resource_viewer::resource_cursor, 2) == 1, "Resource viewer test 6", test_level_normal);
+
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(pe_resource_viewer::resource_cursor, 5) == 0, pe_exception::resource_directory_entry_not_found, "Resource viewer test 7", test_level_normal);
+	PE_TEST(res.get_language_count(pe_resource_viewer::resource_cursor, 2) == 1, "Resource viewer test 8", test_level_normal);
+	
+	PE_TEST(res.get_language_count(pe_resource_viewer::resource_icon_group, L"MAIN_ICON") == 1, "Resource viewer test 9", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(pe_resource_viewer::resource_icon_group, L"DOESNT_EXIST") == 1, pe_exception::resource_directory_entry_not_found, "Resource viewer test 10", test_level_normal);
+
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(L"NONAME", L"DOESNT_EXIST") == 1, pe_exception::resource_directory_entry_not_found, "Resource viewer test 11", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_language_count(L"NONAME", 123) == 1, pe_exception::resource_directory_entry_not_found, "Resource viewer test 12", test_level_normal);
+	
+	PE_TEST(!res.resource_exists(L"NOT_EXISTENT"), "Resource viewer test 13", test_level_normal);
+	PE_TEST(res.resource_exists(pe_resource_viewer::resource_bitmap), "Resource viewer test 14", test_level_normal);
+	
+	PE_TEST(res.list_resource_types().size() == 8, "Resource viewer test 15", test_level_critical);
+	PE_TEST(res.list_resource_types()[7] == pe_resource_viewer::resource_manifest, "Resource viewer test 16", test_level_normal);
+	
+	PE_TEST(res.list_resource_names(pe_resource_viewer::resource_bitmap).size() == 0, "Resource viewer test 17", test_level_critical);
+	PE_TEST(res.list_resource_ids(pe_resource_viewer::resource_bitmap).size() == 3, "Resource viewer test 18", test_level_critical);
+	
+	PE_TEST_EXPECT_EXCEPTION(res.list_resource_names(L"DOESNOT_EXIST"), pe_exception::resource_directory_entry_not_found, "Resource viewer test 19", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.list_resource_ids(L"DOESNOT_EXIST"), pe_exception::resource_directory_entry_not_found, "Resource viewer test 20", test_level_normal);
+	
+	PE_TEST(res.list_resource_ids(pe_resource_viewer::resource_bitmap).at(2) == 103, "Resource viewer test 21", test_level_normal);
+	PE_TEST(res.list_resource_names(pe_resource_viewer::resource_icon_group).size() == 1, "Resource viewer test 22", test_level_critical);
+	PE_TEST(res.list_resource_names(pe_resource_viewer::resource_icon_group).at(0) == L"MAIN_ICON", "Resource viewer test 23", test_level_normal);
+	
+	PE_TEST(res.list_resource_languages(pe_resource_viewer::resource_icon_group, 107).size() == 1, "Resource viewer test 24", test_level_critical);
+	PE_TEST(res.list_resource_languages(pe_resource_viewer::resource_icon_group, 107).at(0) == 1049, "Resource viewer test 25", test_level_normal);
+	
+	PE_TEST(res.list_resource_languages(pe_resource_viewer::resource_icon_group, L"MAIN_ICON").size() == 1, "Resource viewer test 26", test_level_critical);
+	PE_TEST(res.list_resource_languages(pe_resource_viewer::resource_icon_group, L"MAIN_ICON").at(0) == 1049, "Resource viewer test 27", test_level_critical);
+
+	PE_TEST_EXPECT_EXCEPTION(res.list_resource_languages(L"UNEXISTENT", L"MAIN_ICON"), pe_exception::resource_directory_entry_not_found, "Resource viewer test 28", test_level_critical);
+	PE_TEST_EXPECT_EXCEPTION(res.list_resource_languages(L"UNEXISTENT", 123), pe_exception::resource_directory_entry_not_found, "Resource viewer test 29", test_level_critical);
+	
+	PE_TEST(res.get_resource_data_by_id(pe_resource_viewer::resource_manifest, 1).get_codepage() == 0x4E4, "Resource viewer test 30", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(pe_resource_viewer::resource_manifest, 1).get_data().substr(0, 15) == "<assembly xmlns", "Resource viewer test 31", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_id(pe_resource_viewer::resource_manifest, 1, 1), pe_exception::resource_data_entry_not_found, "Resource viewer test 32", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_id(L"NONAME", 1), pe_exception::resource_directory_entry_not_found, "Resource viewer test 33", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_id(1049, L"NONAME", 123), pe_exception::resource_directory_entry_not_found, "Resource viewer test 34", test_level_normal);
+	PE_TEST(res.get_resource_data_by_id(1033, pe_resource_viewer::resource_manifest, 1).get_codepage() == 0x4E4, "Resource viewer test 35", test_level_normal);
+
+	PE_TEST(res.get_resource_data_by_name(pe_resource_viewer::resource_icon_group, L"MAIN_ICON").get_codepage() == 0x4E4, "Resource viewer test 36", test_level_normal);
+	PE_TEST(res.get_resource_data_by_name(pe_resource_viewer::resource_icon_group, L"MAIN_ICON").get_data().substr(0, 5) == std::string("\0\0\1\0\x0d", 5), "Resource viewer test 37", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_name(pe_resource_viewer::resource_icon_group, L"MAIN_ICON", 1), pe_exception::resource_data_entry_not_found, "Resource viewer test 38", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_name(L"NONAME", L"NONAME2"), pe_exception::resource_directory_entry_not_found, "Resource viewer test 39", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_name(1049, L"QWERTY", L"QWERTY"), pe_exception::resource_directory_entry_not_found, "Resource viewer test 40", test_level_normal);
+	PE_TEST(res.get_resource_data_by_name(1049, pe_resource_viewer::resource_icon_group, L"MAIN_ICON").get_codepage() == 0x4E4, "Resource viewer test 41", test_level_normal);
+	
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_id(1032, pe_resource_viewer::resource_manifest, 1), pe_exception::resource_directory_entry_not_found, "Resource viewer test 42", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(res.get_resource_data_by_name(1050, pe_resource_viewer::resource_icon_group, L"MAIN_ICON"), pe_exception::resource_directory_entry_not_found, "Resource viewer test 43", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcproj b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..31ea0ba0136a91c5e11b0bb8cb1fbd6987851540
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resource_viewer"
+	ProjectGUID="{DD6C58C3-6DD5-43B2-A9ED-760E5F5830AA}"
+	RootNamespace="test_resource_viewer"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..ba74aff11534d22ff31eb72ebff31f9972703f6b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{1FC3537C-EC13-4877-A06C-42DD8B81CBF3}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resource_viewer</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resource_viewer/test_resource_viewer.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resources/Makefile b/irdb-lib/pebliss/trunk/tests/test_resources/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resources/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_resources/main.cpp b/irdb-lib/pebliss/trunk/tests/test_resources/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..a84fb940cc2b3044bc919f863a573c3b582dbf3a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resources/main.cpp
@@ -0,0 +1,89 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include <pe_bliss_resources.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void test_resources(const resource_directory& root)
+{
+	PE_TEST(root.get_entry_list().size() == 8, "Resource test 1", test_level_critical);
+	PE_TEST(root.get_characteristics() == 0 && root.get_timestamp() == 0, "Resource test 2", test_level_normal);
+	PE_TEST(root.get_minor_version() == 0 && root.get_major_version() == 4, "Resource test 3", test_level_normal);
+	PE_TEST(root.get_number_of_named_entries() == 0 && root.get_number_of_id_entries() == 8, "Resource test 4", test_level_normal);
+	PE_TEST(!root.get_entry_list()[1].is_named() && root.get_entry_list()[1].get_id() == pe_resource_viewer::resource_bitmap, "Resource test 5", test_level_normal);
+	PE_TEST(!root.get_entry_list()[1].includes_data(), "Resource test 6", test_level_critical);
+
+	const resource_directory& bitmap_root = root.get_entry_list()[1].get_resource_directory();
+	PE_TEST(bitmap_root.get_number_of_named_entries() == 0 && bitmap_root.get_number_of_id_entries() == 3, "Resource test 7", test_level_critical);
+	PE_TEST(!bitmap_root.get_entry_list()[1].is_named() && bitmap_root.get_entry_list()[1].get_id() == 102, "Resource test 8", test_level_normal);
+	PE_TEST(!bitmap_root.get_entry_list()[1].includes_data(), "Resource test 9", test_level_critical);
+	
+	const resource_directory& bitmap_102_root = bitmap_root.get_entry_list()[1].get_resource_directory();
+	PE_TEST(bitmap_102_root.get_number_of_named_entries() == 0 && bitmap_102_root.get_number_of_id_entries() == 1, "Resource test 10", test_level_critical);
+	PE_TEST(!bitmap_102_root.get_entry_list()[0].is_named() && bitmap_102_root.get_entry_list()[0].get_id() == 1049, "Resource test 11", test_level_normal);
+	PE_TEST(bitmap_102_root.get_entry_list()[0].includes_data(), "Resource test 12", test_level_critical);
+	
+	const resource_data_entry& bitmap_data = bitmap_102_root.get_entry_list()[0].get_data_entry();
+	PE_TEST(bitmap_data.get_codepage() == 0x4E4, "Resource test 13", test_level_normal);
+	PE_TEST(bitmap_data.get_data().substr(0, 5) == std::string("\x28\0\0\0\x4f", 5) && bitmap_data.get_data().size() == 0x4EE8, "Resource test 14", test_level_normal);
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	resource_directory root;
+	
+	PE_TEST_EXCEPTION(root = get_resources(image), "Resource Directory Parser test 1", test_level_critical);
+	test_resources(root);
+	
+	section s;
+	s.get_raw_data().resize(1);
+	s.set_name("newrsrc");
+	section& new_resource_section = image.add_section(s);
+	uint32_t old_resources_rva = image.get_directory_rva(pe_win::image_directory_entry_resource);
+	PE_TEST_EXCEPTION(rebuild_resources(image, root, new_resource_section, 0, true, true), "Resource Rebuilder test 1", test_level_critical);
+	PE_TEST_EXCEPTION(root = get_resources(image), "Resource Directory Parser test 2", test_level_critical);
+	PE_TEST(old_resources_rva != image.get_directory_rva(pe_win::image_directory_entry_resource), "Relocation Directory test", test_level_normal);
+	test_resources(root);
+	
+	new_resource_section.set_raw_data("111");
+	PE_TEST_EXCEPTION(rebuild_resources(image, root, new_resource_section, 3, true, true), "Resource Rebuilder test 2", test_level_critical);
+	PE_TEST(new_resource_section.get_raw_data().substr(0, 3) == "111", "Resource Rebuilder Offset test", test_level_normal);
+	PE_TEST_EXCEPTION(root = get_resources(image), "Resource Directory Parser test 3", test_level_critical);
+	test_resources(root);
+
+	PE_TEST_EXCEPTION(rebuild_resources(image, root, new_resource_section, 12, true, true), "Resource Rebuilder test 3", test_level_critical);
+	PE_TEST_EXCEPTION(root = get_resources(image), "Resource Directory Parser test 4", test_level_critical);
+	test_resources(root);
+
+	{
+		resource_directory& cursor_root = root.get_entry_list()[0].get_resource_directory();
+		resource_directory_entry named_entry;
+		named_entry.set_name(L"test entry");
+		named_entry.add_data_entry(resource_data_entry("alala", 123));
+		cursor_root.add_resource_directory_entry(named_entry);
+	}
+
+	PE_TEST_EXCEPTION(rebuild_resources(image, root, new_resource_section, 12, true, true), "Resource Rebuilder test 4", test_level_critical);
+	PE_TEST_EXCEPTION(root = get_resources(image), "Resource Directory Parser test 5", test_level_critical);
+	test_resources(root);
+
+	resource_directory& cursor_root = root.get_entry_list()[0].get_resource_directory();
+	PE_TEST(cursor_root.entry_by_name(L"test entry").get_data_entry().get_data() == "alala", "Resource named entry test", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcproj b/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..bb6f122160579d7dc67d9c8cf97dba7ced3f9705
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_resources"
+	ProjectGUID="{7E3867A9-59BC-4441-A74E-F4ABFFEE231C}"
+	RootNamespace="test_resources"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcxproj b/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..43718c2ff54122831509770ec3de63635b66b598
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{8ECEF4F9-1461-4FCB-87D9-C871C71B01B7}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_resources</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_resources/test_resources.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_rich_data/Makefile b/irdb-lib/pebliss/trunk/tests/test_rich_data/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_rich_data/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_rich_data/main.cpp b/irdb-lib/pebliss/trunk/tests/test_rich_data/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..51027ada7074aa177e1944d53ba51809f495d486
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_rich_data/main.cpp
@@ -0,0 +1,40 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	rich_data_list data;
+	PE_TEST_EXCEPTION(data = get_rich_data(image), "Rich Data test 1", test_level_critical);
+	PE_TEST(data.size() == 8, "Rich Data test 2", test_level_normal);
+	PE_TEST(data[0].get_number() == 158, "Rich Data test 3", test_level_normal);
+
+	if(image.get_pe_type() == pe_type_32)
+	{
+		PE_TEST(data[1].get_times() == 47, "Rich Data test 4", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(data[1].get_times() == 48, "Rich Data test 4", test_level_normal);
+	}
+
+	PE_TEST(data[2].get_version() == 40219, "Rich Data test 5", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcproj b/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..ce50d48e7d4e688ca5fde7c5c87324109e923ef2
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_rich_data"
+	ProjectGUID="{1F877026-3D94-41BF-B392-06DFAF67AE34}"
+	RootNamespace="test_rich_data"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcxproj b/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..a51b0c5ac51028e02b474bfac66088657a408dd0
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{114AC59B-BC28-40DB-8380-67C422D0C81B}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_rich_data</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_rich_data/test_rich_data.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_runner/Makefile b/irdb-lib/pebliss/trunk/tests/test_runner/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_runner/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_runner/main.cpp b/irdb-lib/pebliss/trunk/tests/test_runner/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..69839e67332604516f5b8b98812a6884ea13f6f1
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_runner/main.cpp
@@ -0,0 +1,212 @@
+#include <iostream>
+#include <map>
+#include <string>
+#include <stdio.h>
+#include <pe_bliss.h>
+#ifndef PE_BLISS_WINDOWS
+#include <sys/wait.h>
+#endif
+
+#define PE_TEST_32 "../pe_files/image32.exe"
+#define PE_TEST_64 "../pe_files/image64.exe"
+#define PE_TEST_DOTNET "../pe_files/TestApp.exe"
+#define PE_TEST_DEBUG "../pe_files/debug_test.exe"
+#define PE_DLL_TEST_32 "../pe_files/test_dll_32.dll"
+#define PE_DLL_TEST_64 "../pe_files/test_dll_64.dll"
+#define PE_BOUND_IMPORT_TEST_32 "../pe_files/bound32.exe"
+#define PE_BOUND_IMPORT_TEST_64 "../pe_files/bound64.exe"
+#define PE_TEST_MESSAGE_TABLE "../pe_files/message_table_resource.exe"
+
+class testcase
+{
+public:
+	testcase(const std::string& binary_name, const std::string& testcase_name, const std::vector<std::string>& command_lines = std::vector<std::string>())
+		:binary_name_(binary_name), testcase_name_(testcase_name), command_lines_(command_lines)
+	{}
+
+	const std::string get_binary_name() const
+	{
+#ifdef PE_BLISS_WINDOWS
+		return binary_name_ + ".exe";
+#else
+		return binary_name_;
+#endif
+	}
+
+	const std::string& get_testcase_name() const
+	{
+		return testcase_name_;
+	}
+
+	const std::vector<std::string>& get_command_lines() const
+	{
+		return command_lines_;
+	}
+
+private:
+	std::string binary_name_;
+	std::string testcase_name_;
+	std::vector<std::string> command_lines_;
+};
+
+#ifdef PE_BLISS_WINDOWS
+#define POPEN _popen
+#define PCLOSE _pclose
+#define DEV_NULL " 1> nul"
+#else
+#define POPEN popen
+#define PCLOSE pclose
+#define DEV_NULL " 1> /dev/null"
+#endif
+
+bool run_test(const std::string& path, const std::string& test, bool& warnings_occured, const std::string& cmd = "")
+{
+	FILE* bin;
+#ifdef PE_BLISS_WINDOWS
+		bin = POPEN(("\"\"" + path + test + "\" \"" + path + cmd + "\"\" 2>&1" + DEV_NULL).c_str(), "r");
+#else
+		bin = POPEN(("\"" + path + test + "\" \"" + path + cmd + "\" 2>&1" + DEV_NULL).c_str(), "r");
+#endif
+
+	if(bin == NULL)
+	{
+		std::cerr << "Cannot execute testsuite" << std::endl;
+		return false;
+	}
+
+	char buf[256];
+	while(fgets(buf, sizeof(buf), bin) != NULL)
+	{
+		warnings_occured = true;
+		std::cerr << buf;
+	}
+
+#ifdef PE_BLISS_WINDOWS
+	return PCLOSE(bin) == 0;
+#else
+	int stat;
+	int wstat = WEXITSTATUS(stat = PCLOSE(bin));
+	if(stat < 0 || (wstat != 0 && wstat != 128 + SIGPIPE))
+		return false;
+	else
+		return true;
+#endif
+}
+
+const std::string get_full_path(const std::string& full_name)
+{
+	std::string::size_type slash_pos = full_name.find_last_of("/\\");
+	if(slash_pos != std::string::npos)
+		return full_name.substr(0, slash_pos + 1);
+	
+	return "";
+}
+
+int main(int argc, char* argv[])
+{
+	bool warnings_occured = false;
+
+	typedef std::vector<testcase> test_list;
+
+	test_list tests;
+
+	{
+		std::vector<std::string> command_line;
+		command_line.push_back(PE_TEST_32);
+		command_line.push_back(PE_TEST_64);
+		tests.push_back(testcase("tests_utils", "PE Utils tests"));
+		tests.push_back(testcase("tests_basic", "Basic PE tests", command_line));
+		tests.push_back(testcase("test_checksum", "PE Checksum tests", command_line));
+		tests.push_back(testcase("test_entropy", "PE Entropy tests", command_line));
+		tests.push_back(testcase("test_rich_data", "PE Rich Data tests", command_line));
+		tests.push_back(testcase("test_imports", "PE Imports tests", command_line));
+		tests.push_back(testcase("test_relocations", "PE Relocations tests", command_line));
+		tests.push_back(testcase("test_load_config", "PE Load Configuration tests", command_line));
+		tests.push_back(testcase("test_exception_directory", "PE Exception Directory tests", command_line));
+		tests.push_back(testcase("test_tls", "PE Thread Local Storage tests", command_line));
+		tests.push_back(testcase("test_resources", "PE Resource Directory tests", command_line));
+
+		command_line.pop_back();
+		//These binaries work with resource classes, which are not dependent on PE format
+		//So PE32 is enough to test them
+		tests.push_back(testcase("test_resource_viewer", "PE Resource Viewer tests", command_line));
+		tests.push_back(testcase("test_resource_manager", "PE Resource Manager tests", command_line));
+		tests.push_back(testcase("test_resource_bitmap", "PE Resource Bitmap Read & Write tests", command_line));
+		tests.push_back(testcase("test_resource_icon_cursor", "PE Resource Icon/Cursor Read & Write tests", command_line));
+		tests.push_back(testcase("test_resource_string_table", "PE Resource String Table Parser tests", command_line));
+		tests.push_back(testcase("test_resource_version_info", "PE Resource Version Info & Write tests", command_line));
+	}
+
+	{
+		std::vector<std::string> message_table_command_line;
+		message_table_command_line.push_back(PE_TEST_MESSAGE_TABLE);
+		tests.push_back(testcase("test_resource_message_table", "Pe Resource Message Table Parser tests", message_table_command_line));
+	}
+
+	{
+		std::vector<std::string> dotnet_command_line;
+		dotnet_command_line.push_back(PE_TEST_DOTNET);
+		tests.push_back(testcase("test_dotnet", "PE Basic .NET tests", dotnet_command_line));
+	}
+
+	{
+		std::vector<std::string> debug_command_line;
+		debug_command_line.push_back(PE_TEST_DEBUG);
+		debug_command_line.push_back(PE_TEST_64);
+		tests.push_back(testcase("test_debug", "PE Debug Info tests", debug_command_line));
+	}
+
+	{
+		std::vector<std::string> dll_command_line;
+		dll_command_line.push_back(PE_DLL_TEST_32);
+		dll_command_line.push_back(PE_DLL_TEST_64);
+		tests.push_back(testcase("test_exports", "PE Exports tests", dll_command_line));
+	}
+
+	{
+		std::vector<std::string> bound_import_command_line;
+		bound_import_command_line.push_back(PE_BOUND_IMPORT_TEST_32);
+		bound_import_command_line.push_back(PE_BOUND_IMPORT_TEST_64);
+		tests.push_back(testcase("test_bound_import", "PE Bound Import tests", bound_import_command_line));
+	}
+
+	std::string runner_path(get_full_path(argv[0]));
+	
+	for(test_list::const_iterator it = tests.begin(); it != tests.end(); ++it)
+	{
+		const testcase& t = *it;
+		bool result = true;
+		if(!t.get_command_lines().empty())
+		{
+			const std::vector<std::string>& cmd_lines = t.get_command_lines();
+			for(std::vector<std::string>::const_iterator cmd = cmd_lines.begin(); cmd != cmd_lines.end(); ++cmd)
+			{
+				std::cout << "Running " << t.get_testcase_name() << " with \"" << (*cmd) << "\"" << std::endl;
+				result = run_test(runner_path, t.get_binary_name(), warnings_occured, *cmd);
+				if(!result)
+					break;
+			}
+		}
+		else
+		{
+			std::cout << "Running " << t.get_testcase_name() << std::endl;
+			result = run_test(runner_path, t.get_binary_name(), warnings_occured);
+		}
+
+		if(!result)
+		{
+			std::cerr << "Some tests hard-failed in this testsuite, exiting..." << std::endl;
+			return -1;
+		}
+
+		std::cout << std::endl;
+	}
+
+	if(warnings_occured)
+		std::cout << "Some tests failed, check the log!" << std::endl;
+	else
+		std::cout << "Everything went just fine!" << std::endl;
+
+	std::cout << "Finished." << std::endl;
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcproj b/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..73c1ed9f48b62d67173fa2e4fd858ad870cc363b
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcproj
@@ -0,0 +1,351 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_runner"
+	ProjectGUID="{31843E48-DC9A-4887-BD97-328079D78C88}"
+	RootNamespace="test_runner"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcxproj b/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..9b86e96c00b09ccbe0f4071fbb10c5b2d85a813c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcxproj
@@ -0,0 +1,163 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{132DFCC9-13EF-4178-9772-1C467FB296D6}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_runner</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8755a3a0268981c2f6fee186ee23f9488c6d781c
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_runner/test_runner.vcxproj.filters
@@ -0,0 +1,22 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_tls/Makefile b/irdb-lib/pebliss/trunk/tests/test_tls/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_tls/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/test_tls/main.cpp b/irdb-lib/pebliss/trunk/tests/test_tls/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..802147c793a352143b02cf40663c7a256a2aba6a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_tls/main.cpp
@@ -0,0 +1,101 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+void test_tls(const tls_info& info, const pe_base& image, bool check_callbacks = true)
+{
+	PE_TEST(info.get_characteristics() == 0, "TLS test 1", test_level_normal);
+	PE_TEST(info.get_size_of_zero_fill() == 0, "TLS test 2", test_level_normal);
+	PE_TEST(info.get_raw_data_end_rva() - info.get_raw_data_start_rva() == 8, "TLS test 3", test_level_normal);
+	PE_TEST(info.get_raw_data() == std::string("\0\0\0\0\x37\x02\0\0", 8), "TLS test 4", test_level_normal);
+
+	if(check_callbacks)
+	{
+		PE_TEST(info.get_tls_callbacks().empty(), "TLS test 5", test_level_normal);
+	}
+
+	if(image.get_pe_type() == pe_type_32)
+	{
+		PE_TEST(info.get_index_rva() == 0x420738 - image.get_image_base_32(), "TLS test 6", test_level_normal);
+
+		if(check_callbacks)
+		{
+			PE_TEST(info.get_callbacks_rva() == 0x418188 - image.get_image_base_32(), "TLS test 7", test_level_normal);
+		}
+	}
+	else
+	{
+		PE_TEST(info.get_index_rva() == 0x14002647Cull - image.get_image_base_64(), "TLS test 6", test_level_normal);
+
+		if(check_callbacks)
+		{
+			PE_TEST(info.get_callbacks_rva() == 0x14001B310ull - image.get_image_base_64(), "TLS test 7", test_level_normal);
+		}
+	}
+}
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+		
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	pe_base image(pe_factory::create_pe(*pe_file));
+	
+	tls_info info;
+	PE_TEST_EXCEPTION(info = get_tls_info(image), "TLS Parser test 1", test_level_critical);
+	test_tls(info, image);
+
+	section s;
+	s.get_raw_data().resize(1);
+	s.set_name("newtls");
+	section& new_tls_section = image.add_section(s);
+	uint32_t old_tls_rva = image.get_directory_rva(pe_win::image_directory_entry_tls);
+	PE_TEST_EXCEPTION(rebuild_tls(image, info, new_tls_section, 0, false, false, tls_data_expand_raw, true, true), "TLS Rebuilder test 1", test_level_critical);
+	PE_TEST(old_tls_rva != image.get_directory_rva(pe_win::image_directory_entry_tls), "TLS directory test", test_level_normal);
+
+	PE_TEST_EXCEPTION(info = get_tls_info(image), "TLS Parser test 2", test_level_critical);
+	test_tls(info, image);
+	
+	new_tls_section.set_raw_data("111");
+	PE_TEST_EXCEPTION(rebuild_tls(image, info, new_tls_section, 3, false, false, tls_data_expand_raw, true, true), "TLS Rebuilder test 2", test_level_critical);
+	PE_TEST_EXCEPTION(info = get_tls_info(image), "TLS Parser test 3", test_level_critical);
+	PE_TEST(new_tls_section.get_raw_data().substr(0, 3) == "111", "TLS Rebuilder offset test", test_level_normal);
+	test_tls(info, image);
+	
+	PE_TEST_EXCEPTION(rebuild_tls(image, info, new_tls_section, 12, false, false, tls_data_expand_raw, true, true), "TLS Rebuilder test 3", test_level_critical);
+	PE_TEST_EXCEPTION(info = get_tls_info(image), "TLS Parser test 4", test_level_critical);
+	test_tls(info, image);
+	
+	image.set_section_virtual_size(new_tls_section, 0x2000);
+	info.set_raw_data_start_rva(image.rva_from_section_offset(new_tls_section, 0x1000));
+	info.recalc_raw_data_end_rva();
+	PE_TEST_EXCEPTION(rebuild_tls(image, info, new_tls_section, 12, false, true, tls_data_expand_raw, true, true), "TLS Rebuilder test 4", test_level_critical);
+	PE_TEST_EXCEPTION(info = get_tls_info(image), "TLS Parser test 5", test_level_critical);
+	test_tls(info, image);
+	
+	info.add_tls_callback(0x111);
+	info.add_tls_callback(0x222);
+	info.add_tls_callback(0x333);
+	info.add_tls_callback(0x444);
+	info.add_tls_callback(0x555);
+	info.set_callbacks_rva(image.rva_from_section_offset(new_tls_section, 0x1500));
+
+	PE_TEST_EXCEPTION(rebuild_tls(image, info, new_tls_section, 12, true, true, tls_data_expand_raw, true, true), "TLS Rebuilder test 5", test_level_critical);
+	PE_TEST_EXCEPTION(info = get_tls_info(image), "TLS Parser test 6", test_level_critical);
+	test_tls(info, image, false);
+	PE_TEST(info.get_tls_callbacks().size() == 5, "TLS test 7", test_level_normal);
+	PE_TEST(info.get_tls_callbacks()[2] == 0x333, "TLS test 8", test_level_normal);
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcproj b/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..457589e1d7f8aefc2f77069fd8da5d46e4238c9f
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="test_tls"
+	ProjectGUID="{63D80BC8-EB14-4698-A391-4A41AC15E8D1}"
+	RootNamespace="test_tls"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcxproj b/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..d7e555f9074f52d8aeb79ce1a7655648319cdce5
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{CFC22F11-2C5F-46F3-9C51-ED8C3E5EFA89}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>test_tls</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/test_tls/test_tls.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/tests.mak b/irdb-lib/pebliss/trunk/tests/tests.mak
new file mode 100644
index 0000000000000000000000000000000000000000..430bcdcc1db27a9a81c90f1e425807ccd8591f19
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests.mak
@@ -0,0 +1,23 @@
+PWD=$(shell pwd)
+OUTDIR = ../bin/
+LIBPATH = ../../lib/libpebliss.a
+NAME=$(shell basename $(PWD))
+CXXFLAGS = -O2 -Wall -I../../pe_lib -I../
+
+ifdef PE_DEBUG
+CXXFLAGS  += -g -O0
+endif
+
+all: $(OUTDIR)$(NAME)
+
+clean:
+	rm -f $(NAME) *.o
+	rm -f $(OUTDIR)$(NAME)
+
+$(NAME): main.o
+	$(CXX) -Wall $^ -lpebliss -L../../lib -o $(NAME) -liconv
+
+main.o: $(LIBPATH)
+
+$(OUTDIR)$(NAME): $(NAME)
+	cp -d $(NAME) $(OUTDIR)
diff --git a/irdb-lib/pebliss/trunk/tests/tests_basic/Makefile b/irdb-lib/pebliss/trunk/tests/tests_basic/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_basic/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/tests_basic/main.cpp b/irdb-lib/pebliss/trunk/tests/tests_basic/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..487ceda9dc04dc8545a66685d35edf61aa6d53e6
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_basic/main.cpp
@@ -0,0 +1,496 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+	
+	std::auto_ptr<std::ifstream> pe_file;
+	if(!open_pe_file(argc, argv, pe_file))
+		return -1;
+
+	std::auto_ptr<pe_base> image;
+	PE_TEST_EXCEPTION(image.reset(new pe_base(pe_factory::create_pe(*pe_file))), "Creation, type detection and copying test", test_level_critical);
+	
+	PE_TEST(!image->has_overlay(), "Overlay test", test_level_normal);
+	PE_TEST(image->get_stub_overlay()[1] == 0x1F, "Stub test 1", test_level_normal);
+	PE_TEST_EXCEPTION(image->fill_stub_overlay(0x11), "Stub test 2", test_level_normal);
+	PE_TEST(image->get_stub_overlay()[1] == 0x11, "Stub test 3", test_level_normal);
+	PE_TEST_EXCEPTION(image->strip_stub_overlay(), "Stub test 4", test_level_normal);
+	PE_TEST(image->get_stub_overlay().empty(), "Stub test 5", test_level_normal);
+
+	std::cout << "PE Header tests..." << std::endl;
+
+	PE_TEST(!image->directory_exists(pe_win::image_directory_entry_com_descriptor), "Directory test 1", test_level_normal);
+	PE_TEST(image->directory_exists(pe_win::image_directory_entry_import), "Directory test 2", test_level_normal);
+	PE_TEST(image->has_imports(), "Directory test 3", test_level_normal);
+	PE_TEST(!image->has_exports(), "Directory test 4", test_level_normal);
+
+	PE_TEST(image->get_subsystem() == pe_win::image_subsystem_windows_cui, "Subsystem test 1", test_level_normal);
+	PE_TEST(image->is_console(), "Subsystem test 2", test_level_normal);
+	PE_TEST(!image->is_gui(), "Subsystem test 3", test_level_normal);
+
+	image->set_subsystem(pe_win::image_subsystem_native_windows);
+	PE_TEST(image->get_subsystem() == pe_win::image_subsystem_native_windows, "Subsystem test 4", test_level_normal);
+
+	PE_TEST(image->get_pe_signature() == 0x4550, "PE Signature test", test_level_normal);
+
+	PE_TEST(image->get_file_alignment() == 0x200, "File Alignment test 1", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(image->set_file_alignment(123), pe_exception::incorrect_file_alignment, "File Alignment test 2", test_level_normal);
+	PE_TEST_EXCEPTION(image->set_file_alignment(0x1000), "File Alignment test 3", test_level_normal);
+	PE_TEST(image->get_file_alignment() == 0x1000, "File Alignment test 4", test_level_normal);
+
+	PE_TEST(image->get_section_alignment() == 0x1000, "Section Alignment test", test_level_normal);
+
+	PE_TEST(image->get_number_of_rvas_and_sizes() == 0x10, "Data directories test", test_level_normal);
+
+	PE_TEST(image->check_characteristics_flag(pe_win::image_file_executable_image), "Image Characteristics test 1", test_level_normal);
+	PE_TEST(!image->check_characteristics_flag(pe_win::image_file_dll), "Image Characteristics test 2", test_level_normal);
+
+	PE_TEST(image->get_size_of_headers() == 0x400, "Size of headers test", test_level_normal);
+
+	PE_TEST(image->get_dll_characteristics() == 0x8140, "Image DLL Characteristics test", test_level_normal);
+
+	if(image->get_pe_type() == pe_type_32)
+	{
+		PE_TEST(image->get_directory_rva(pe_win::image_directory_entry_import) == 0x1C9E4, "Directory RVA test 1", test_level_normal);
+		PE_TEST(image->get_directory_size(pe_win::image_directory_entry_import) == 0x3C, "Directory size test 1", test_level_normal);
+
+		PE_TEST(image->get_minor_os_version() == 1 && image->get_major_os_version() == 5, "OS Version test", test_level_normal);
+		PE_TEST(image->get_minor_subsystem_version() == 1 && image->get_major_subsystem_version() == 5, "Subsystem Version test", test_level_normal);
+
+		PE_TEST(image->get_pe_header_start() == 0xE0, "e_lfanew test", test_level_normal);
+
+		PE_TEST(image->get_size_of_image() == 0x41000, "Size of Image test", test_level_normal);
+		PE_TEST(image->get_ep() == 0x6851, "Entry Point test", test_level_normal);
+
+		PE_TEST(image->get_characteristics() == 0x102, "Image Characteristics test 3", test_level_normal);
+
+		PE_TEST(image->get_size_of_optional_header() == 0xE0, "Size of optional header test", test_level_normal);
+
+		PE_TEST(image->get_magic() == 0x10B, "PE Magic test", test_level_normal);
+
+		PE_TEST(image->get_image_base_32() == 0x400000, "Image Base test 1", test_level_normal);
+
+		{
+			uint32_t image_base;
+			image->get_image_base(image_base);
+			PE_TEST(image_base == 0x400000, "Image Base test 2", test_level_normal);
+		}
+
+		PE_TEST(image->get_heap_size_commit_32() == 0x1000, "Heap Size Commit test 1", test_level_normal);
+		PE_TEST(image->get_heap_size_reserve_32() == 0x100000, "Heap Size Reserve test 1", test_level_normal);
+		PE_TEST(image->get_stack_size_commit_32() == 0x1000, "Stack Size Commit test 1", test_level_normal);
+		PE_TEST(image->get_stack_size_reserve_32() == 0x100000, "Stack Size Reserve test 1", test_level_normal);
+
+		{
+			uint32_t size;
+			image->get_heap_size_commit(size);
+			PE_TEST(size == 0x1000, "Heap Size Commit test 2", test_level_normal);
+			image->get_heap_size_reserve(size);
+			PE_TEST(size == 0x100000, "Heap Size Reserve test 2", test_level_normal);
+			image->get_stack_size_commit(size);
+			PE_TEST(size == 0x1000, "Stack Size Commit test 2", test_level_normal);
+			image->get_stack_size_reserve(size);
+			PE_TEST(size == 0x100000, "Stack Size Reserve test 2", test_level_normal);
+		}
+
+		PE_TEST(image->get_time_date_stamp() == 0x508E65A3, "TimeStamp test", test_level_normal);
+		PE_TEST(image->get_machine() == 0x014C, "Machine test", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(image->get_directory_rva(pe_win::image_directory_entry_import) == 0x223EC, "Directory RVA test", test_level_normal);
+		PE_TEST(image->get_directory_size(pe_win::image_directory_entry_import) == 0x3C, "Directory size test", test_level_normal);
+
+		PE_TEST(image->get_pe_header_start() == 0xF0, "e_lfanew test", test_level_normal);
+
+		PE_TEST(image->get_minor_os_version() == 2 && image->get_major_os_version() == 5, "OS Version test", test_level_normal);
+		PE_TEST(image->get_minor_subsystem_version() == 2 && image->get_major_subsystem_version() == 5, "Subsystem Version test", test_level_normal);
+
+		PE_TEST(image->get_size_of_image() == 0x48000, "Size of Image test", test_level_normal);
+		PE_TEST(image->get_ep() == 0x7A64, "Entry Point test", test_level_normal);
+
+		PE_TEST(image->get_characteristics() == 0x22, "Image Characteristics test 3", test_level_normal);
+
+		PE_TEST(image->get_size_of_optional_header() == 0xF0, "Size of optional header test", test_level_normal);
+
+		PE_TEST(image->get_magic() == 0x20B, "PE Magic test", test_level_normal);
+
+		PE_TEST(image->get_image_base_64() == 0x0000000140000000ull, "Image Base test 1", test_level_normal);
+
+		{
+			uint64_t image_base;
+			image->get_image_base(image_base);
+			PE_TEST(image_base == 0x0000000140000000ull, "Image Base test 2", test_level_normal);
+		}
+
+		PE_TEST(image->get_heap_size_commit_64() == 0x1000, "Heap Size Commit test 1", test_level_normal);
+		PE_TEST(image->get_heap_size_reserve_64() == 0x100000, "Heap Size Reserve test 1", test_level_normal);
+		PE_TEST(image->get_stack_size_commit_64() == 0x1000, "Stack Size Commit test 1", test_level_normal);
+		PE_TEST(image->get_stack_size_reserve_64() == 0x100000, "Stack Size Reserve test 1", test_level_normal);
+
+		{
+			uint64_t size;
+			image->get_heap_size_commit(size);
+			PE_TEST(size == 0x1000, "Heap Size Commit test 2", test_level_normal);
+			image->get_heap_size_reserve(size);
+			PE_TEST(size == 0x100000, "Heap Size Reserve test 2", test_level_normal);
+			image->get_stack_size_commit(size);
+			PE_TEST(size == 0x1000, "Stack Size Commit test 2", test_level_normal);
+			image->get_stack_size_reserve(size);
+			PE_TEST(size == 0x100000, "Stack Size Reserve test 2", test_level_normal);
+		}
+
+		PE_TEST(image->get_time_date_stamp() == 0x508E65B2, "TimeStamp test", test_level_normal);
+		PE_TEST(image->get_machine() == 0x8664, "Machine test", test_level_normal);
+	}
+
+	image->set_directory_rva(pe_win::image_directory_entry_architecture, 0x1000);
+	image->set_directory_size(pe_win::image_directory_entry_architecture, 0x2000);
+	PE_TEST(image->get_directory_rva(pe_win::image_directory_entry_architecture) == 0x1000, "Directory RVA test 2", test_level_normal);
+	PE_TEST(image->get_directory_size(pe_win::image_directory_entry_architecture) == 0x2000, "Directory size test 2", test_level_normal);
+
+	image->remove_directory(pe_win::image_directory_entry_architecture);
+	PE_TEST(image->get_directory_rva(pe_win::image_directory_entry_architecture) == 0, "Directory RVA test 3", test_level_normal);
+	PE_TEST(image->get_directory_size(pe_win::image_directory_entry_architecture) == 0, "Directory size test 3", test_level_normal);
+
+	PE_TEST(image->strip_data_directories(0, false) == 0x10 - 3, "Data directories strip test 1", test_level_normal);
+	PE_TEST(image->get_number_of_rvas_and_sizes() == 0x10 - 3, "Data directories strip test 2", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(image->get_directory_rva(pe_win::image_directory_entry_com_descriptor) == 0, pe_exception::directory_does_not_exist, "Directory RVA test 4", test_level_normal);
+	PE_TEST_EXPECT_EXCEPTION(image->get_directory_size(pe_win::image_directory_entry_com_descriptor) == 0, pe_exception::directory_does_not_exist, "Directory size test 4", test_level_normal);
+	
+	if(image->get_pe_type() == pe_type_32)
+	{
+		PE_TEST(image->strip_data_directories(0, true) == 0x10 - 5, "Data directories strip test 3", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(image->strip_data_directories(0, true) == 0x10 - 6, "Data directories strip test 3", test_level_normal);
+	}
+
+	std::cout << "Address tests..." << std::endl;
+
+	if(image->get_pe_type() == pe_type_32)
+	{
+		PE_TEST(image->va_to_rva(image->get_image_base_32() + 1) == 1, "Address conversion test 1", test_level_normal);
+		PE_TEST_EXPECT_EXCEPTION(image->va_to_rva(image->get_image_base_32() - 1), pe_exception::incorrect_address_conversion, "Address conversion test 2", test_level_normal);
+		PE_TEST(image->rva_to_va_32(1) == image->get_image_base_32() + 1, "Address conversion test 3", test_level_normal);
+
+		{
+			uint32_t va;
+			image->rva_to_va(1, va);
+			PE_TEST(va == image->get_image_base_32() + 1, "Address conversion test 4", test_level_normal);
+		}
+	}
+	else
+	{
+		PE_TEST(image->va_to_rva(image->get_image_base_64() + 1) == 1, "Address conversion test 1", test_level_normal);
+		PE_TEST_EXPECT_EXCEPTION(image->va_to_rva(image->get_image_base_64() - 1), pe_exception::incorrect_address_conversion, "Address conversion test 2", test_level_normal);
+		PE_TEST(image->rva_to_va_64(1) == image->get_image_base_64() + 1, "Address conversion test 3", test_level_normal);
+
+		{
+			uint64_t va;
+			image->rva_to_va(1, va);
+			PE_TEST(va == image->get_image_base_64() + 1, "Address conversion test 4", test_level_normal);
+		}
+	}
+
+	PE_TEST(image->rva_to_file_offset(0x1001) == 0x401, "Address conversion test 5", test_level_normal);
+	PE_TEST(image->file_offset_to_rva(0x401) == 0x1001, "Address conversion test 6", test_level_normal);
+	PE_TEST(image->file_offset_to_rva(0x1) == 0x1, "Address conversion test 7", test_level_normal);
+	PE_TEST(image->rva_to_file_offset(0x1) == 0x1, "Address conversion test 8", test_level_normal);
+
+
+	std::cout << "Section tests..." << std::endl;
+	if(image->get_pe_type() == pe_type_32)
+	{
+		PE_TEST(image->get_number_of_sections() == 0x6, "Section number test 1", test_level_normal);
+	}
+	else
+	{
+		PE_TEST(image->get_number_of_sections() == 0x7, "Section number test 1", test_level_normal);
+	}
+
+	PE_TEST(image->get_image_sections().size() == image->get_number_of_sections(), "Section number test 2", test_level_critical);
+
+	PE_TEST(image->get_image_sections().at(0).get_name() == ".text", "Section name test 1", test_level_normal);
+	PE_TEST(image->get_image_sections().at(1).get_name() == ".rdata", "Section name test 2", test_level_normal);
+
+	PE_TEST(image->section_from_directory(pe_win::image_directory_entry_import).get_name() == ".rdata", "Section test 1", test_level_normal);
+	PE_TEST(image->section_from_rva(0x1000).get_name() == ".text", "Section test 2", test_level_normal);
+	PE_TEST(image->section_from_va(image->get_image_base_64() + 0x1000).get_name() == ".text", "Section test 3", test_level_normal);
+	PE_TEST(image->section_from_file_offset(0x401).get_name() == ".text", "Section test 4", test_level_normal);
+	PE_TEST(image->rva_from_section_offset(image->get_image_sections().at(0), 0x5) == 0x1005, "Section test 5", test_level_normal);
+
+	{
+		const section& s = image->get_image_sections().at(0);
+		PE_TEST(image->section_data_length_from_rva(s.get_virtual_address() + 123, section_data_raw, false) == s.get_raw_data().size(), "Section test 6", test_level_normal);
+		PE_TEST(image->section_data_length_from_rva(s, s.get_virtual_address() + 123, section_data_raw) == s.get_raw_data().size() - 123, "Section test 7", test_level_normal);
+		PE_TEST(image->section_data_length_from_rva(s.get_virtual_address() + 123, s.get_virtual_address() + 123, section_data_raw, false) == s.get_raw_data().size() - 123, "Section test 8", test_level_normal);
+
+		PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_rva(s, s.get_virtual_address() - 1, section_data_raw), pe_exception::rva_not_exists, "Section test 9", test_level_normal);
+		PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_rva(s.get_virtual_address() + 123, s.get_virtual_address() - 1, section_data_raw, false), pe_exception::rva_not_exists, "Section test 10", test_level_normal);
+
+		PE_TEST(image->section_data_length_from_rva(s.get_virtual_address() + 123, section_data_virtual, false) == s.get_aligned_virtual_size(image->get_section_alignment()), "Section test 11", test_level_normal);
+		PE_TEST(image->section_data_length_from_rva(s, s.get_virtual_address() + 123, section_data_virtual) == s.get_aligned_virtual_size(image->get_section_alignment()) - 123, "Section test 12", test_level_normal);
+		PE_TEST(image->section_data_length_from_rva(s.get_virtual_address() + 123, s.get_virtual_address() + 123, section_data_virtual, false) == s.get_aligned_virtual_size(image->get_section_alignment()) - 123, "Section test 13", test_level_normal);
+
+		PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_rva(s, s.get_virtual_address() - 1, section_data_virtual), pe_exception::rva_not_exists, "Section test 14", test_level_normal);
+		PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_rva(s.get_virtual_address() + 123, s.get_virtual_address() - 1, section_data_virtual, false), pe_exception::rva_not_exists, "Section test 15", test_level_normal);
+
+		if(image->get_pe_type() == pe_type_32)
+		{
+			uint32_t base = image->get_image_base_32();
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, section_data_raw, false) == s.get_raw_data().size(), "Section test 16", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(s, base + s.get_virtual_address() + 123, section_data_raw) == s.get_raw_data().size() - 123, "Section test 17", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() + 123, section_data_raw, false) == s.get_raw_data().size() - 123, "Section test 18", test_level_normal);
+
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(s, base + s.get_virtual_address() - 1, section_data_raw), pe_exception::rva_not_exists, "Section test 19", test_level_normal);
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() - 1, section_data_raw, false), pe_exception::rva_not_exists, "Section test 20", test_level_normal);
+
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, section_data_virtual, false) == s.get_aligned_virtual_size(image->get_section_alignment()), "Section test 21", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(s, base + s.get_virtual_address() + 123, section_data_virtual) == s.get_aligned_virtual_size(image->get_section_alignment()) - 123, "Section test 22", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() + 123, section_data_virtual, false) == s.get_aligned_virtual_size(image->get_section_alignment()) - 123, "Section test 23", test_level_normal);
+
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(s, base + s.get_virtual_address() - 1, section_data_virtual), pe_exception::rva_not_exists, "Section test 24", test_level_normal);
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() - 1, section_data_virtual, false), pe_exception::rva_not_exists, "Section test 25", test_level_normal);
+
+			PE_TEST(image->section_data_from_rva<uint32_t>(0x1005, section_data_raw, false) == 0x505BE900, "Section data test 1", test_level_normal);
+			PE_TEST(image->section_data_from_rva<uint32_t>(s, 0x1005, section_data_raw) == 0x505BE900, "Section data test 2", test_level_normal);
+
+			PE_TEST(image->section_data_from_va<uint32_t>(base + 0x1005, section_data_raw, false) == 0x505BE900, "Section data test 3", test_level_normal);
+			PE_TEST(image->section_data_from_va<uint32_t>(s, base + 0x1005, section_data_raw) == 0x505BE900, "Section data test 4", test_level_normal);
+
+			PE_TEST(image->section_data_from_rva<uint32_t>(0x1005, section_data_virtual, false) == 0x505BE900, "Section data test 5", test_level_normal);
+			PE_TEST(image->section_data_from_rva<uint32_t>(s, 0x1005, section_data_virtual) == 0x505BE900, "Section data test 6", test_level_normal);
+
+			PE_TEST(image->section_data_from_va<uint32_t>(base + 0x1005, section_data_virtual, false) == 0x505BE900, "Section data test 7", test_level_normal);
+			PE_TEST(image->section_data_from_va<uint32_t>(s, base + 0x1005, section_data_virtual) == 0x505BE900, "Section data test 8", test_level_normal);
+
+			PE_TEST(image->section_data_from_rva<uint32_t>(0x1, section_data_raw, true) == 0x0300905A, "Section data test 9", test_level_normal);
+			PE_TEST(image->section_data_from_va<uint32_t>(base + 0x1, section_data_raw, true) == 0x0300905A, "Section data test 10", test_level_normal);
+
+			PE_TEST(*image->section_data_from_rva(0x1005, section_data_raw, false) == 0x00, "Section data test 11", test_level_normal);
+			PE_TEST(*image->section_data_from_rva(s, 0x1005, section_data_raw) == 0x00, "Section data test 12", test_level_normal);
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_from_rva(s, 0x999, section_data_raw), pe_exception::rva_not_exists, "Section data test 13", test_level_normal);
+
+			PE_TEST(*image->section_data_from_va(base + 0x1005, section_data_raw, false) == 0x00, "Section data test 14", test_level_normal);
+			PE_TEST(*image->section_data_from_va(s, base + 0x1005, section_data_raw) == 0x00, "Section data test 15", test_level_normal);
+
+			PE_TEST(*image->section_data_from_rva(0x1E000 + 0x388C, section_data_virtual, false) == 0x00, "Section data test 16", test_level_normal);
+		}
+		else
+		{
+			uint64_t base = image->get_image_base_64();
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, section_data_raw, false) == s.get_raw_data().size(), "Section test 16", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(s, base + s.get_virtual_address() + 123, section_data_raw) == s.get_raw_data().size() - 123, "Section test 17", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() + 123, section_data_raw, false) == s.get_raw_data().size() - 123, "Section test 18", test_level_normal);
+
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(s, base + s.get_virtual_address() - 1, section_data_raw), pe_exception::rva_not_exists, "Section test 19", test_level_normal);
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() - 1, section_data_raw, false), pe_exception::rva_not_exists, "Section test 20", test_level_normal);
+
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, section_data_virtual, false) == s.get_aligned_virtual_size(image->get_section_alignment()), "Section test 21", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(s, base + s.get_virtual_address() + 123, section_data_virtual) == s.get_aligned_virtual_size(image->get_section_alignment()) - 123, "Section test 22", test_level_normal);
+			PE_TEST(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() + 123, section_data_virtual, false) == s.get_aligned_virtual_size(image->get_section_alignment()) - 123, "Section test 23", test_level_normal);
+
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(s, base + s.get_virtual_address() - 1, section_data_virtual), pe_exception::rva_not_exists, "Section test 24", test_level_normal);
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_length_from_va(base + s.get_virtual_address() + 123, base + s.get_virtual_address() - 1, section_data_virtual, false), pe_exception::rva_not_exists, "Section test 25", test_level_normal);
+
+			PE_TEST(image->section_data_from_rva<uint32_t>(0x1005, section_data_raw, false) == 0x89480001, "Section data test 1", test_level_normal);
+			PE_TEST(image->section_data_from_rva<uint32_t>(s, 0x1005, section_data_raw) == 0x89480001, "Section data test 2", test_level_normal);
+
+			PE_TEST(image->section_data_from_va<uint32_t>(base + 0x1005, section_data_raw, false) == 0x89480001, "Section data test 3", test_level_normal);
+			PE_TEST(image->section_data_from_va<uint32_t>(s, base + 0x1005, section_data_raw) == 0x89480001, "Section data test 4", test_level_normal);
+
+			PE_TEST(image->section_data_from_rva<uint32_t>(0x1005, section_data_virtual, false) == 0x89480001, "Section data test 5", test_level_normal);
+			PE_TEST(image->section_data_from_rva<uint32_t>(s, 0x1005, section_data_virtual) == 0x89480001, "Section data test 6", test_level_normal);
+
+			PE_TEST(image->section_data_from_va<uint32_t>(base + 0x1005, section_data_virtual, false) == 0x89480001, "Section data test 7", test_level_normal);
+			PE_TEST(image->section_data_from_va<uint32_t>(s, base + 0x1005, section_data_virtual) == 0x89480001, "Section data test 8", test_level_normal);
+
+			PE_TEST(image->section_data_from_rva<uint32_t>(0x1, section_data_raw, true) == 0x0300905A, "Section data test 9", test_level_normal);
+			PE_TEST(image->section_data_from_va<uint32_t>(base + 0x1, section_data_raw, true) == 0x0300905A, "Section data test 10", test_level_normal);
+
+			PE_TEST(*image->section_data_from_rva(0x1005, section_data_raw, false) == 0x01, "Section data test 11", test_level_normal);
+			PE_TEST(*image->section_data_from_rva(s, 0x1005, section_data_raw) == 0x01, "Section data test 12", test_level_normal);
+			PE_TEST_EXPECT_EXCEPTION(image->section_data_from_rva(s, 0x999, section_data_raw), pe_exception::rva_not_exists, "Section data test 13", test_level_normal);
+
+			PE_TEST(*image->section_data_from_va(base + 0x1005, section_data_raw, false) == 0x01, "Section data test 14", test_level_normal);
+			PE_TEST(*image->section_data_from_va(s, base + 0x1005, section_data_raw) == 0x01, "Section data test 15", test_level_normal);
+
+			PE_TEST(*image->section_data_from_rva(0x23000 + 0x46F0, section_data_virtual, false) == 0x00, "Section data test 16", test_level_normal);
+		}
+	}
+	
+	PE_TEST(image->section_and_offset_from_rva(0x1005).first == 5, "Section data test 17", test_level_normal);
+	PE_TEST(image->section_and_offset_from_rva(0x1005).second->get_name() == ".text", "Section data test 18", test_level_normal);
+	
+	PE_TEST(image->section_data_length_from_rva(1, section_data_raw, true) == image->get_size_of_headers(), "Section test 26", test_level_normal);
+	PE_TEST(image->section_data_length_from_rva(1, 1, section_data_raw, true) == image->get_size_of_headers() - 1, "Section test 27", test_level_normal);
+
+	if(image->get_pe_type() == pe_type_32)
+	{
+		uint32_t base = image->get_image_base_32();
+		PE_TEST(image->section_data_length_from_va(base + 1, section_data_raw, true) == image->get_size_of_headers(), "Section test 28", test_level_normal);
+		PE_TEST(image->section_data_length_from_va(base + 1, base + 1, section_data_raw, true) == image->get_size_of_headers() - 1, "Section test 29", test_level_normal);
+	}
+	else
+	{
+		uint64_t base = image->get_image_base_64();
+		PE_TEST(image->section_data_length_from_va(base + 1, section_data_raw, true) == image->get_size_of_headers(), "Section test 28", test_level_normal);
+		PE_TEST(image->section_data_length_from_va(base + 1, base + 1, section_data_raw, true) == image->get_size_of_headers() - 1, "Section test 29", test_level_normal);
+	}
+
+	PE_TEST(image->section_attached(image->get_image_sections().at(0)), "Section data test 30", test_level_normal);
+	PE_TEST(!image->section_attached(section()), "Section data test 31", test_level_normal);
+
+
+	{
+		const section& s = image->get_image_sections().at(0);
+		PE_TEST(s.get_characteristics() == 0x60000020, "Section class test 1", test_level_normal);
+		PE_TEST(s.get_name() == ".text", "Section class test 2", test_level_normal);
+		PE_TEST(s.get_pointer_to_raw_data() == 0x400, "Section class test 3", test_level_normal);
+		PE_TEST(s.get_virtual_address() == 0x1000, "Section class test 4", test_level_normal);
+
+		if(image->get_pe_type() == pe_type_32)
+		{
+			PE_TEST(s.get_size_of_raw_data() == 0x16E00, "Section class test 5", test_level_normal);
+			PE_TEST(s.get_virtual_size() == 0x16C0D, "Section class test 6", test_level_normal);
+		}
+		else
+		{
+			PE_TEST(s.get_size_of_raw_data() == 0x19400, "Section class test 5", test_level_normal);
+			PE_TEST(s.get_virtual_size() == 0x1923E, "Section class test 6", test_level_normal);
+		}
+		
+		PE_TEST(s.readable(), "Section class test 7", test_level_normal);
+		PE_TEST(s.executable(), "Section class test 8", test_level_normal);
+		PE_TEST(!s.writeable(), "Section class test 9", test_level_normal);
+		PE_TEST(!s.shared(), "Section class test 10", test_level_normal);
+		PE_TEST(!s.discardable(), "Section class test 11", test_level_normal);
+		PE_TEST(!s.empty(), "Section class test 12", test_level_normal);
+	}
+
+	{
+		section s;
+		PE_TEST_EXPECT_EXCEPTION(image->prepare_section(s), pe_exception::zero_section_sizes, "Prepare Section test 1", test_level_normal);
+	}
+
+	{
+		section s;
+		s.set_raw_data("123");
+		PE_TEST_EXCEPTION(image->prepare_section(s), "Prepare Section test 2", test_level_normal);
+		PE_TEST(s.get_virtual_size() == pe_utils::align_up(s.get_size_of_raw_data(), image->get_file_alignment()), "Prepare Section test 3", test_level_normal);
+
+		uint16_t old_sections_count = image->get_number_of_sections();
+		uint16_t old_size_of_image = image->get_size_of_image();
+		PE_TEST_EXCEPTION(image->add_section(s), "Add section test 1", test_level_normal);
+		PE_TEST(image->get_number_of_sections() == old_sections_count + 1, "Add section test 2", test_level_normal);
+		PE_TEST(image->get_image_sections().back().get_raw_data() == "123", "Add section test 3", test_level_normal);
+		PE_TEST(image->get_size_of_image() > old_size_of_image, "Add section test 4", test_level_normal);
+	}
+
+	{
+		section s;
+		s.set_raw_data(std::string("123\0\0\0", 6));
+		PE_TEST_EXCEPTION(image->recalculate_section_sizes(s, true), "recalculate_section_sizes test 1", test_level_normal);
+		PE_TEST(s.get_raw_data() == "123", "recalculate_section_sizes test 2", test_level_normal);
+	}
+
+	PE_TEST_EXPECT_EXCEPTION(image->set_section_virtual_size(image->get_image_sections().at(0), 0x100), pe_exception::error_changing_section_virtual_size, "set_section_virtual_size test 1", test_level_normal);
+
+	{
+		section s;
+		PE_TEST_EXPECT_EXCEPTION(image->set_section_virtual_size(s, 0), pe_exception::error_changing_section_virtual_size, "set_section_virtual_size test 2", test_level_normal);
+	}
+
+	PE_TEST_EXCEPTION(image->set_section_virtual_size(image->get_image_sections().back(), 0x1000), "set_section_virtual_size test 3", test_level_normal);
+	PE_TEST(image->get_image_sections().back().get_virtual_size() == 0x1000, "set_section_virtual_size test 4", test_level_normal);
+
+	image->set_file_alignment(0x1000);
+	PE_TEST_EXCEPTION(image->realign_all_sections(), "Section realigning test", test_level_normal);
+	PE_TEST_EXCEPTION(image->realign_file(0x200), "File realigning test", test_level_normal);
+
+	{
+		section& s = image->get_image_sections().back();
+		PE_TEST_EXPECT_EXCEPTION(image->expand_section(s, s.get_virtual_address() + 0x5000, 0x1000, pe_base::expand_section_raw), pe_exception::rva_not_exists, "Section expand test 1", test_level_normal);
+		PE_TEST(image->expand_section(s, s.get_virtual_address() + 0x100, 0x1000, pe_base::expand_section_raw) == true, "Section expand test 2", test_level_normal);
+		PE_TEST(s.get_virtual_size() >= 0x100 + 0x1000, "Section expand test 3", test_level_normal);
+		PE_TEST(s.get_size_of_raw_data() >= 0x100 + 0x1000, "Section expand test 4", test_level_normal);
+
+		uint32_t old_raw_size = s.get_size_of_raw_data();
+		PE_TEST(image->expand_section(s, s.get_virtual_address() + 0x100, 0x5000, pe_base::expand_section_virtual) == true, "Section expand test 5", test_level_normal);
+		PE_TEST(s.get_virtual_size() >= 0x100 + 0x5000, "Section expand test 6", test_level_normal);
+		PE_TEST(old_raw_size == s.get_size_of_raw_data(), "Section expand test 7", test_level_normal);
+		PE_TEST(image->expand_section(s, s.get_virtual_address() + 0x100, 0x1000, pe_base::expand_section_raw) == false, "Section expand test 8", test_level_normal);
+		PE_TEST(image->expand_section(s, s.get_virtual_address() + 0x100, 0x5000, pe_base::expand_section_virtual) == false, "Section expand test 9", test_level_normal);
+	}
+
+	{
+		image->get_image_sections().pop_back();
+
+		std::stringstream new_pe(std::ios::in | std::ios::out | std::ios::binary);
+		PE_TEST_EXCEPTION(rebuild_pe(*image, new_pe, false, true, true), "Rebuild PE test 1", test_level_critical);
+
+		std::auto_ptr<pe_base> new_image;
+		PE_TEST_EXCEPTION(new_image.reset(new pe_base(pe_factory::create_pe(new_pe))), "Creation, type detection and copying test 2", test_level_critical);
+		
+		section_list& sections = image->get_image_sections();
+		section_list& new_sections = new_image->get_image_sections();
+		PE_TEST(sections.size() == new_sections.size(), "Rebuild PE test 2", test_level_normal);
+
+		for(uint32_t i = 0; i != sections.size(); ++i)
+		{
+			std::string raw_data_old(sections[i].get_raw_data());
+			std::string raw_data_new(new_sections[i].get_raw_data());
+			pe_utils::strip_nullbytes(raw_data_old);
+			pe_utils::strip_nullbytes(raw_data_new);
+			
+			std::cout << "Rebuilt PE test iteration " << i << std::endl;
+			PE_TEST(raw_data_old == raw_data_new, "Rebuild PE test (section raw data compare)", test_level_normal);
+			PE_TEST(sections[i].get_virtual_address() == new_sections[i].get_virtual_address(), "Rebuild PE test (section virtual addresses compare)", test_level_normal);
+			PE_TEST(sections[i].get_aligned_virtual_size(image->get_section_alignment()) == new_sections[i].get_aligned_virtual_size(new_image->get_section_alignment()), "Rebuild PE test (section virtual sizes compare)", test_level_normal);
+		}
+
+
+		new_pe.str("");
+		PE_TEST_EXCEPTION(rebuild_pe(*image, new_pe, true, true, true), "Rebuild PE test 3", test_level_critical);
+		PE_TEST_EXCEPTION(new_image.reset(new pe_base(pe_factory::create_pe(new_pe))), "Creation, type detection and copying test 3", test_level_critical);
+		
+		image->set_stub_overlay("123");
+		new_pe.str("");
+		PE_TEST_EXCEPTION(rebuild_pe(*image, new_pe, false, true, true), "Rebuild PE test 4", test_level_critical);
+		PE_TEST_EXCEPTION(new_image.reset(new pe_base(pe_factory::create_pe(new_pe))), "Creation, type detection and copying test 4", test_level_critical);
+		new_pe.str("");
+		PE_TEST_EXCEPTION(rebuild_pe(*image, new_pe, true, true, true), "Rebuild PE test 5", test_level_critical);
+		PE_TEST_EXCEPTION(new_image.reset(new pe_base(pe_factory::create_pe(new_pe))), "Creation, type detection and copying test 5", test_level_critical);
+	}
+
+
+	{
+		pe_base new_pe(pe_properties_32(), 0x1000, false, pe_win::image_subsystem_windows_cui);
+		PE_TEST(new_pe.get_section_alignment() == 0x1000, "Empty PE Creation test 1", test_level_normal);
+		PE_TEST(new_pe.get_subsystem() == pe_win::image_subsystem_windows_cui, "Empty PE Creation test 2", test_level_normal);
+		PE_TEST(!new_pe.check_characteristics_flag(pe_win::image_file_dll), "Empty PE Creation test 3", test_level_normal);
+		
+		std::stringstream new_pe_data(std::ios::in | std::ios::out | std::ios::binary);
+		PE_TEST_EXCEPTION(rebuild_pe(new_pe, new_pe_data, false, true), "Rebuild PE test 3", test_level_critical);
+
+		std::auto_ptr<pe_base> new_pe_after_rebuild;
+		PE_TEST_EXCEPTION(new_pe_after_rebuild.reset(new pe_base(pe_factory::create_pe(new_pe_data))), "Creation, type detection and copying test 4", test_level_critical);
+		PE_TEST(new_pe_after_rebuild->get_section_alignment() == 0x1000, "Empty PE Read test 1", test_level_normal);
+		PE_TEST(new_pe_after_rebuild->get_number_of_sections() == 0, "Empty PE Read test 2", test_level_normal);
+	}
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcproj b/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..c69523410d829a54366ea88626ccdddbf86d874a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="tests_basic"
+	ProjectGUID="{3451AE03-3363-445B-8DA8-94B197563D59}"
+	RootNamespace="tests_basic"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcxproj b/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..70e1846a9dcb28fce91f78e950b2b7bc77f037aa
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{7870A9AC-92BB-423B-BC03-FBF7B46CD338}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>tests_basic</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_basic/tests_basic.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/tests_utils/Makefile b/irdb-lib/pebliss/trunk/tests/tests_utils/Makefile
new file mode 100644
index 0000000000000000000000000000000000000000..422827f1e3ba0c0d1373f3dcd0b7219c702e806e
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_utils/Makefile
@@ -0,0 +1 @@
+include ../tests.mak
diff --git a/irdb-lib/pebliss/trunk/tests/tests_utils/main.cpp b/irdb-lib/pebliss/trunk/tests/tests_utils/main.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..1db6212f78720cec140f3e13ebac9306d6084bff
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_utils/main.cpp
@@ -0,0 +1,52 @@
+#include <iostream>
+#include <fstream>
+#include <pe_bliss.h>
+#define PE_FILES_UNUSED
+#include "test.h"
+#ifdef PE_BLISS_WINDOWS
+#include "lib.h"
+#endif
+
+using namespace pe_bliss;
+
+int main(int argc, char* argv[])
+{
+	PE_TEST_START
+
+	const char data[] = "abcdefgh";
+	PE_TEST(pe_utils::is_null_terminated(data, sizeof(data)), "is_null_terminated test 1", test_level_normal);
+	PE_TEST(!pe_utils::is_null_terminated(data, sizeof(data) - 1), "is_null_terminated test 2", test_level_normal);
+
+	std::string str("test\0\0\0");
+	PE_TEST_EXCEPTION(pe_utils::strip_nullbytes(str), "strip_nullbytes test 1", test_level_normal);
+	PE_TEST(str == "test", "strip_nullbytes test 2", test_level_normal);
+
+	PE_TEST(pe_utils::is_power_of_2(8), "is_power_of_2 test 1", test_level_normal);
+	PE_TEST(!pe_utils::is_power_of_2(7), "is_power_of_2 test 2", test_level_normal);
+
+	PE_TEST(pe_utils::align_down(99, 4) == 96, "align_down test 1", test_level_normal);
+	PE_TEST(pe_utils::align_down(100, 4) == 100, "align_down test 2", test_level_normal);
+
+	PE_TEST(pe_utils::align_up(99, 4) == 100, "align_up test 1", test_level_normal);
+	PE_TEST(pe_utils::align_up(100, 4) == 100, "align_up test 2", test_level_normal);
+
+	PE_TEST(pe_utils::is_sum_safe(100, 100), "is_sum_safe test 1", test_level_normal);
+	PE_TEST(!pe_utils::is_sum_safe(pe_utils::max_dword - 1, 2), "is_sum_safe test 2", test_level_normal);
+
+	std::ifstream file(argv[0]);
+	file.seekg(0, std::ios::end);
+	std::streamoff size = file.tellg();
+	file.seekg(123);
+
+	PE_TEST(pe_utils::get_file_size(file) == size, "get_file_size test 1", test_level_normal);
+	PE_TEST(static_cast<std::streamoff>(file.tellg()) == static_cast<std::streamoff>(123), "get_file_size test 2", test_level_normal); //Restore position test
+
+#ifndef PE_BLISS_WINDOWS
+	PE_TEST(pe_utils::from_ucs2(pe_utils::to_ucs2(L"alala")) == L"alala", "to_ucs2 & from_ucs2 test 1", test_level_normal);
+	PE_TEST(pe_utils::from_ucs2(pe_utils::to_ucs2(L"")) == L"", "to_ucs2 & from_ucs2 test 2", test_level_normal);
+#endif
+
+	PE_TEST_END
+
+	return 0;
+}
diff --git a/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcproj b/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcproj
new file mode 100644
index 0000000000000000000000000000000000000000..43861cf957ab800fc315a8a157e420b8a07a7bcb
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcproj
@@ -0,0 +1,359 @@
+<?xml version="1.0" encoding="windows-1251"?>
+<VisualStudioProject
+	ProjectType="Visual C++"
+	Version="9,00"
+	Name="tests_utils"
+	ProjectGUID="{B0478C25-73AD-4085-BA1A-DDF66431EB6E}"
+	RootNamespace="tests_utils"
+	Keyword="Win32Proj"
+	TargetFrameworkVersion="196613"
+	>
+	<Platforms>
+		<Platform
+			Name="Win32"
+		/>
+		<Platform
+			Name="x64"
+		/>
+	</Platforms>
+	<ToolFiles>
+	</ToolFiles>
+	<Configurations>
+		<Configuration
+			Name="Debug|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="4"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|Win32"
+			OutputDirectory="$(SolutionDir)$(ConfigurationName)"
+			IntermediateDirectory="$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="WIN32;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="1"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Debug|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="0"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;_DEBUG;_CONSOLE"
+				MinimalRebuild="true"
+				BasicRuntimeChecks="3"
+				RuntimeLibrary="1"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="2"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+		<Configuration
+			Name="Release|x64"
+			OutputDirectory="$(SolutionDir)$(PlatformName)\$(ConfigurationName)"
+			IntermediateDirectory="$(PlatformName)\$(ConfigurationName)"
+			ConfigurationType="1"
+			CharacterSet="1"
+			WholeProgramOptimization="1"
+			>
+			<Tool
+				Name="VCPreBuildEventTool"
+			/>
+			<Tool
+				Name="VCCustomBuildTool"
+			/>
+			<Tool
+				Name="VCXMLDataGeneratorTool"
+			/>
+			<Tool
+				Name="VCWebServiceProxyGeneratorTool"
+			/>
+			<Tool
+				Name="VCMIDLTool"
+				TargetEnvironment="3"
+			/>
+			<Tool
+				Name="VCCLCompilerTool"
+				Optimization="2"
+				EnableIntrinsicFunctions="true"
+				AdditionalIncludeDirectories="../../pe_lib/;../"
+				PreprocessorDefinitions="_WIN64;NDEBUG;_CONSOLE"
+				RuntimeLibrary="0"
+				EnableFunctionLevelLinking="true"
+				UsePrecompiledHeader="0"
+				WarningLevel="3"
+				DebugInformationFormat="3"
+			/>
+			<Tool
+				Name="VCManagedResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCResourceCompilerTool"
+			/>
+			<Tool
+				Name="VCPreLinkEventTool"
+			/>
+			<Tool
+				Name="VCLinkerTool"
+				LinkIncremental="1"
+				GenerateDebugInformation="true"
+				SubSystem="1"
+				OptimizeReferences="2"
+				EnableCOMDATFolding="2"
+				TargetMachine="17"
+			/>
+			<Tool
+				Name="VCALinkTool"
+			/>
+			<Tool
+				Name="VCManifestTool"
+			/>
+			<Tool
+				Name="VCXDCMakeTool"
+			/>
+			<Tool
+				Name="VCBscMakeTool"
+			/>
+			<Tool
+				Name="VCFxCopTool"
+			/>
+			<Tool
+				Name="VCAppVerifierTool"
+			/>
+			<Tool
+				Name="VCPostBuildEventTool"
+				CommandLine="copy /Y &quot;$(TargetPath)&quot; &quot;$(ProjectDir)..\..\tests\bin\&quot;"
+			/>
+		</Configuration>
+	</Configurations>
+	<References>
+	</References>
+	<Files>
+		<Filter
+			Name="Source Files"
+			Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
+			UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
+			>
+			<File
+				RelativePath=".\main.cpp"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Header Files"
+			Filter="h;hpp;hxx;hm;inl;inc;xsd"
+			UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
+			>
+			<File
+				RelativePath="..\lib.h"
+				>
+			</File>
+			<File
+				RelativePath="..\test.h"
+				>
+			</File>
+		</Filter>
+		<Filter
+			Name="Resource Files"
+			Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav"
+			UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
+			>
+		</Filter>
+	</Files>
+	<Globals>
+	</Globals>
+</VisualStudioProject>
diff --git a/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcxproj b/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcxproj
new file mode 100644
index 0000000000000000000000000000000000000000..2f02942415aaf04fcecae2105d5fb1f2eafc2127
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcxproj
@@ -0,0 +1,167 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup Label="ProjectConfigurations">
+    <ProjectConfiguration Include="Debug|Win32">
+      <Configuration>Debug</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Debug|x64">
+      <Configuration>Debug</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|Win32">
+      <Configuration>Release</Configuration>
+      <Platform>Win32</Platform>
+    </ProjectConfiguration>
+    <ProjectConfiguration Include="Release|x64">
+      <Configuration>Release</Configuration>
+      <Platform>x64</Platform>
+    </ProjectConfiguration>
+  </ItemGroup>
+  <PropertyGroup Label="Globals">
+    <ProjectGuid>{50212477-1614-49C9-9791-4AC72025DC76}</ProjectGuid>
+    <Keyword>Win32Proj</Keyword>
+    <RootNamespace>tests_utils</RootNamespace>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>true</UseDebugLibraries>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
+    <ConfigurationType>Application</ConfigurationType>
+    <UseDebugLibraries>false</UseDebugLibraries>
+    <WholeProgramOptimization>true</WholeProgramOptimization>
+    <CharacterSet>Unicode</CharacterSet>
+  </PropertyGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
+  <ImportGroup Label="ExtensionSettings">
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
+  </ImportGroup>
+  <PropertyGroup Label="UserMacros" />
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <LinkIncremental>true</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <LinkIncremental>false</LinkIncremental>
+  </PropertyGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
+    <ClCompile>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <WarningLevel>Level3</WarningLevel>
+      <Optimization>Disabled</Optimization>
+      <PreprocessorDefinitions>_WIN64;_DEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>WIN32;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
+    <ClCompile>
+      <WarningLevel>Level3</WarningLevel>
+      <PrecompiledHeader>
+      </PrecompiledHeader>
+      <Optimization>MaxSpeed</Optimization>
+      <FunctionLevelLinking>true</FunctionLevelLinking>
+      <IntrinsicFunctions>true</IntrinsicFunctions>
+      <PreprocessorDefinitions>_WIN64;NDEBUG;_CONSOLE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
+      <AdditionalIncludeDirectories>../../pe_lib/;../</AdditionalIncludeDirectories>
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>
+    </ClCompile>
+    <Link>
+      <SubSystem>Console</SubSystem>
+      <GenerateDebugInformation>true</GenerateDebugInformation>
+      <EnableCOMDATFolding>true</EnableCOMDATFolding>
+      <OptimizeReferences>true</OptimizeReferences>
+    </Link>
+    <PostBuildEvent>
+      <Command>copy /Y "$(TargetPath)" "$(ProjectDir)..\..\tests\bin\"</Command>
+    </PostBuildEvent>
+  </ItemDefinitionGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp" />
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h" />
+    <ClInclude Include="..\test.h" />
+  </ItemGroup>
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
+  <ImportGroup Label="ExtensionTargets">
+  </ImportGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcxproj.filters b/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcxproj.filters
new file mode 100644
index 0000000000000000000000000000000000000000..8f0719260417c2cc422a533c4a0c453eb3d84c1a
--- /dev/null
+++ b/irdb-lib/pebliss/trunk/tests/tests_utils/tests_utils.vcxproj.filters
@@ -0,0 +1,30 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <ItemGroup>
+    <Filter Include="Source Files">
+      <UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
+      <Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
+    </Filter>
+    <Filter Include="Header Files">
+      <UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
+      <Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
+    </Filter>
+    <Filter Include="Resource Files">
+      <UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
+      <Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
+    </Filter>
+  </ItemGroup>
+  <ItemGroup>
+    <ClCompile Include="main.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
+  </ItemGroup>
+  <ItemGroup>
+    <ClInclude Include="..\lib.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+    <ClInclude Include="..\test.h">
+      <Filter>Header Files</Filter>
+    </ClInclude>
+  </ItemGroup>
+</Project>
\ No newline at end of file
diff --git a/irdb-lib/plugins_install/add_confinement_section.sh b/irdb-lib/plugins_install/add_confinement_section.sh
new file mode 100755
index 0000000000000000000000000000000000000000..de8ce41834d0859683637a71ac9461c81c57fc83
--- /dev/null
+++ b/irdb-lib/plugins_install/add_confinement_section.sh
@@ -0,0 +1,4 @@
+
+cp a.ncexe a.ncexe.orig
+$STRATA_HOME/tools/pc_confinement/add_confinement_section.sh a.ncexe.orig a.ncexe
+
diff --git a/irdb-lib/plugins_install/assurance_case_evidence.sh b/irdb-lib/plugins_install/assurance_case_evidence.sh
new file mode 100755
index 0000000000000000000000000000000000000000..c10f2f7b87cab4eedca72c341bead4a098f1cca1
--- /dev/null
+++ b/irdb-lib/plugins_install/assurance_case_evidence.sh
@@ -0,0 +1,13 @@
+#!/bin/bash -x
+
+# check for the logs directory
+if [ -d logs ]; then
+	# Gather the relevant lines and print to stdout
+	grep -h ATTRIBUTE logs/* | grep :: | sed "s/# ATTRIBUTE//g"
+
+else
+	echo "ERROR: assurance_case_evidence: no logs directory."
+	exit 1
+fi
+
+exit 0
diff --git a/irdb-lib/plugins_install/cgc_optimize_start.sh b/irdb-lib/plugins_install/cgc_optimize_start.sh
new file mode 100755
index 0000000000000000000000000000000000000000..a494580fba3ec1feea6dd690ad0301f71b1eb65b
--- /dev/null
+++ b/irdb-lib/plugins_install/cgc_optimize_start.sh
@@ -0,0 +1,2 @@
+
+$DAFFY_HOME/dead_code_ident/optimize_start.sh a.ncexe
diff --git a/irdb-lib/plugins_install/concolic.sh b/irdb-lib/plugins_install/concolic.sh
new file mode 100755
index 0000000000000000000000000000000000000000..d84f8317ebd85e8e35c2ba04af57b6556935b4e5
--- /dev/null
+++ b/irdb-lib/plugins_install/concolic.sh
@@ -0,0 +1,4 @@
+
+
+$PEASOUP_HOME/tools/do_concolic.sh a -z $PEASOUP_UMBRELLA_DIR/grace.conf
+
diff --git a/irdb-lib/plugins_install/controlled_exit.sh b/irdb-lib/plugins_install/controlled_exit.sh
new file mode 100755
index 0000000000000000000000000000000000000000..54f7cd7c035190b2a4e827e5742d8a4ec7a9e4c9
--- /dev/null
+++ b/irdb-lib/plugins_install/controlled_exit.sh
@@ -0,0 +1,2 @@
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_CONTROLLED_EXIT 1
diff --git a/irdb-lib/plugins_install/create_binary_script.sh b/irdb-lib/plugins_install/create_binary_script.sh
new file mode 100755
index 0000000000000000000000000000000000000000..3b7f2b2b8059c21cb5b02080b933c3580c5a899c
--- /dev/null
+++ b/irdb-lib/plugins_install/create_binary_script.sh
@@ -0,0 +1,3 @@
+
+$PEASOUP_HOME/tools/do_makepeasoupbinary2.sh a
+
diff --git a/irdb-lib/plugins_install/detect_server.sh b/irdb-lib/plugins_install/detect_server.sh
new file mode 100755
index 0000000000000000000000000000000000000000..fca1498126f042b90ee83abb83f6927ca58165b6
--- /dev/null
+++ b/irdb-lib/plugins_install/detect_server.sh
@@ -0,0 +1,2 @@
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_DETECT_SERVERS 1
diff --git a/irdb-lib/plugins_install/diehard.sh b/irdb-lib/plugins_install/diehard.sh
new file mode 100755
index 0000000000000000000000000000000000000000..e052b12c28aa9bf2d8f09e08ce46a106eaecf432
--- /dev/null
+++ b/irdb-lib/plugins_install/diehard.sh
@@ -0,0 +1,54 @@
+#!/bin/bash
+
+if [ ! -f $CFAR_HOME/DieHard/src/libdiehard-4k-x64.so ]; then
+	echo "ERROR: DieHard library not built/found" | tee warning.txt
+	exit 1
+fi
+
+$PEASOUP_HOME/tools/update_env_var.sh DO_DIEHARD 1
+
+seq=""
+while [[ $# -gt 0 ]]
+do
+key="$1"
+case $key in
+	--structured_heap)
+		seq="$2"
+		shift
+		shift
+	;;
+	*)
+		shift
+	;;
+esac
+done
+
+file a.ncexe |grep -q "64-bit"
+
+if  (file a.ncexe |grep -q "64-bit") ; then 
+	echo "Detected 64-bit binary" 
+	ext=x64
+else 
+	echo "Detected 32-bit binary" 
+	ext=x32
+fi
+
+if [ -z "$seq" ]; then
+	cp $CFAR_HOME/DieHard/src/libdiehard-32k-$ext.so libheaprand.so
+else
+	if [ ! -f $CFAR_HOME/DieHard/src/libdiehard-4k-$ext.so ]; then
+		echo "ERROR: DieHard library 4k not built/found" | tee warning.txt
+		exit 1
+	fi
+
+	if [ ! -f $CFAR_HOME/DieHard/src/libdiehard-32k-$ext.so ]; then
+		echo "ERROR: DieHard library 32k not built/found" | tee warning.txt
+		exit 1
+	fi
+
+	if [ $(expr ${seq} % 2) = 0 ]; then
+		cp $CFAR_HOME/DieHard/src/libdiehard-32k-$ext.so libheaprand.so
+	else
+		cp $CFAR_HOME/DieHard/src/libdiehard-4k-$ext.so libheaprand.so
+	fi
+fi
diff --git a/irdb-lib/plugins_install/double_free.sh b/irdb-lib/plugins_install/double_free.sh
new file mode 100755
index 0000000000000000000000000000000000000000..fbe81b00919bce5b25d6b74eee5e279acfea1e05
--- /dev/null
+++ b/irdb-lib/plugins_install/double_free.sh
@@ -0,0 +1,2 @@
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_DOUBLE_FREE 1
diff --git a/irdb-lib/plugins_install/generate_variant_config.sh b/irdb-lib/plugins_install/generate_variant_config.sh
new file mode 100755
index 0000000000000000000000000000000000000000..5b67f9714922fb8b042894dab3c290ce492f1794
--- /dev/null
+++ b/irdb-lib/plugins_install/generate_variant_config.sh
@@ -0,0 +1,57 @@
+#!/bin/bash -x
+
+backend="zipr"
+
+# check if strata was on from it's log.
+if [  -f logs/stratafy_with_pc_confine.log ]; then
+	backend="strata"
+fi
+
+if [ $backend = "zipr" ]; then
+	echo Found zipr backend.
+
+	template=$PEASOUP_HOME/tools/cfar_configs/zipr_variant.json.template;
+
+
+
+elif [ $backend = "strata" ]; then
+
+	echo "Found strata backend."
+	template=$PEASOUP_HOME/tools/cfar_configs/strata_variant.json.template
+
+else
+	echo Unknown backend.
+	exit 1
+fi
+
+
+# calc stuffs needed.
+base_peasoup_dir=$(basename $newdir)
+exe=$(basename $protected_exe)
+
+# get and fill in template.
+cp $template variant_config.json
+sed -i "s/<<EXE_NAME>>/$exe/g"  variant_config.json
+sed -i "s|<<PS_DIR>>|$base_peasoup_dir|g" variant_config.json
+
+#
+# note that these are all hard-coded in the config files right now.
+# plan:  mine these values out of ps_run.sh and replace in config file.
+#
+#"STRATA_LOG=detectors",
+#"PEASOUP_SCHEDULE_PERTURB=0",
+#"STRATA_WATCHDOG=0",
+#"STRATA_NUM_HANDLE=0",
+#"STRATA_DOUBLE_FREE=0",
+#"STRATA_HEAPRAND=0",
+#"STRATA_SHADOW_STACK=0",
+#"STRATA_CONTROLLED_EXIT=0",
+#"STRATA_DETECT_SERVERS=0",
+#"STRATA_PC_CONFINE=0",
+#"STRATA_PC_CONFINE_XOR=0",
+#"STRATA_REKEY_AFTER=0",
+#"STRATA_PC_CONFINE_XOR_KEY_LENGTH=1024",
+#"STRATA_IS_SO=0",
+#"STRATA_MAX_WARNINGS=500000"
+
+exit 0
diff --git a/irdb-lib/plugins_install/heaprand.sh b/irdb-lib/plugins_install/heaprand.sh
new file mode 100755
index 0000000000000000000000000000000000000000..31194836964047aa1fc24fe7eaa6aef6b83c0e24
--- /dev/null
+++ b/irdb-lib/plugins_install/heaprand.sh
@@ -0,0 +1,2 @@
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_HEAPRAND 1
diff --git a/irdb-lib/plugins_install/ibtl.sh b/irdb-lib/plugins_install/ibtl.sh
new file mode 100755
index 0000000000000000000000000000000000000000..4384aa5cba9ed4f5c1a7dec3579fe1d8a59fd8ae
--- /dev/null
+++ b/irdb-lib/plugins_install/ibtl.sh
@@ -0,0 +1,3 @@
+
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_IBTL 1
diff --git a/irdb-lib/plugins_install/is_so.sh b/irdb-lib/plugins_install/is_so.sh
new file mode 100755
index 0000000000000000000000000000000000000000..7bd11b2eedef7b9c693d96c31ba7a672a4c40770
--- /dev/null
+++ b/irdb-lib/plugins_install/is_so.sh
@@ -0,0 +1,4 @@
+
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_IS_SO $($PEASOUP_HOME/tools/is_so.sh a.ncexe)
+
diff --git a/irdb-lib/plugins_install/isr.sh b/irdb-lib/plugins_install/isr.sh
new file mode 100755
index 0000000000000000000000000000000000000000..de35fc27643b8dda22e514929b224e5f566f2a5a
--- /dev/null
+++ b/irdb-lib/plugins_install/isr.sh
@@ -0,0 +1,2 @@
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_PC_CONFINE_XOR 1
diff --git a/irdb-lib/plugins_install/libtwitcher.sh b/irdb-lib/plugins_install/libtwitcher.sh
new file mode 100755
index 0000000000000000000000000000000000000000..cd1743d340905234164ac3ed98d559218a7e4ee0
--- /dev/null
+++ b/irdb-lib/plugins_install/libtwitcher.sh
@@ -0,0 +1,3 @@
+
+cp $GT_COLLAB_HOME/downloads/libtwitcher.so libheaprand.so
+
diff --git a/irdb-lib/plugins_install/noh.sh b/irdb-lib/plugins_install/noh.sh
new file mode 100755
index 0000000000000000000000000000000000000000..c4b8a2ccf2dbd8338469ec32bab0e7f184983a9e
--- /dev/null
+++ b/irdb-lib/plugins_install/noh.sh
@@ -0,0 +1 @@
+cp $CFAR_HOME/non_overlapping_heap/noh.so noh.so
diff --git a/irdb-lib/plugins_install/nol.sh b/irdb-lib/plugins_install/nol.sh
new file mode 100755
index 0000000000000000000000000000000000000000..797a408cfb45130af91f2f6673f989aba1ddaf9b
--- /dev/null
+++ b/irdb-lib/plugins_install/nol.sh
@@ -0,0 +1,4 @@
+#!/bin/bash 
+
+cp $CFAR_HOME/non_overlapping_libraries/ld-nol.so.ubuntu . || exit 1
+cp $CFAR_HOME/non_overlapping_libraries/ld-nol.so.centos . || exit 1
diff --git a/irdb-lib/plugins_install/output_spec.sh b/irdb-lib/plugins_install/output_spec.sh
new file mode 100755
index 0000000000000000000000000000000000000000..d0696a161cc494e3d3e38bfee365dea9791495d1
--- /dev/null
+++ b/irdb-lib/plugins_install/output_spec.sh
@@ -0,0 +1,35 @@
+#!/bin/bash -x
+
+
+varid="$1"
+fileopt="$2"
+file="$3"
+
+usage()
+{
+	echo "
+
+Usage:
+
+	output_spec.sh <varid> --file 'file1.attr file2.attr ...'
+
+"
+}
+
+main()
+{
+
+	if [ "X$fileopt" != "X--file" ]; then
+		usage
+		exit 1
+	fi
+
+	echo "# ATTRIBUTE backend=$backend" $i >  $file
+	echo "# ATTRIBUTE peasoup_dir=$newdir" $i >>  $file
+	echo "# ATTRIBUTE output_file=$stratafied_exe" $i >>  $file
+	echo "# ATTRIBUTE pwd=$PWD" $i >>  $file
+
+
+}
+
+main "$@"
diff --git a/irdb-lib/plugins_install/pc_confine.sh b/irdb-lib/plugins_install/pc_confine.sh
new file mode 100755
index 0000000000000000000000000000000000000000..36355db8c0cfc525d7c5b8f95071eabdee05a545
--- /dev/null
+++ b/irdb-lib/plugins_install/pc_confine.sh
@@ -0,0 +1,2 @@
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_PC_CONFINE 1
diff --git a/irdb-lib/plugins_install/rekey.sh b/irdb-lib/plugins_install/rekey.sh
new file mode 100755
index 0000000000000000000000000000000000000000..bc9e3a83cbb4431b12a32b2f54e38f55c70744ab
--- /dev/null
+++ b/irdb-lib/plugins_install/rekey.sh
@@ -0,0 +1,4 @@
+
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_REKEY_AFTER 5000
+
diff --git a/irdb-lib/plugins_install/signconv_func_monitor.sh b/irdb-lib/plugins_install/signconv_func_monitor.sh
new file mode 100755
index 0000000000000000000000000000000000000000..9eeaf06b20eba30cbd7612fa28a59199fa0fa293
--- /dev/null
+++ b/irdb-lib/plugins_install/signconv_func_monitor.sh
@@ -0,0 +1,3 @@
+
+
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_NUM_HANDLE 1
diff --git a/irdb-lib/plugins_install/stratafy_with_pc_confine.sh b/irdb-lib/plugins_install/stratafy_with_pc_confine.sh
new file mode 100755
index 0000000000000000000000000000000000000000..90f2059ccc76debac9b001a5d4af080a04b6a4b2
--- /dev/null
+++ b/irdb-lib/plugins_install/stratafy_with_pc_confine.sh
@@ -0,0 +1,2 @@
+
+sh $STRATA_HOME/tools/pc_confinement/stratafy_with_pc_confine.sh a.ncexe a.stratafied
diff --git a/irdb-lib/plugins_install/test.exe b/irdb-lib/plugins_install/test.exe
new file mode 100755
index 0000000000000000000000000000000000000000..7daf5cd461c7392b817d6aba7a9cffd577c85412
--- /dev/null
+++ b/irdb-lib/plugins_install/test.exe
@@ -0,0 +1,3 @@
+#/bin/sh 
+
+echo this is a test of a shell script in plugins_install with args = "$@"
diff --git a/irdb-lib/plugins_install/test.sh b/irdb-lib/plugins_install/test.sh
new file mode 100755
index 0000000000000000000000000000000000000000..7daf5cd461c7392b817d6aba7a9cffd577c85412
--- /dev/null
+++ b/irdb-lib/plugins_install/test.sh
@@ -0,0 +1,3 @@
+#/bin/sh 
+
+echo this is a test of a shell script in plugins_install with args = "$@"
diff --git a/irdb-lib/plugins_install/watchdog.sh b/irdb-lib/plugins_install/watchdog.sh
new file mode 100755
index 0000000000000000000000000000000000000000..ae3002757a9c0712aee3ba5717118c9aaaac455d
--- /dev/null
+++ b/irdb-lib/plugins_install/watchdog.sh
@@ -0,0 +1,3 @@
+
+watchdog_val=30
+$PEASOUP_HOME/tools/update_env_var.sh STRATA_WATCHDOG $watchdog_val
diff --git a/irdb-lib/plugins_install/zipr.sh b/irdb-lib/plugins_install/zipr.sh
new file mode 100755
index 0000000000000000000000000000000000000000..e37c8e25d4b4dc694940221a3cd62ec0f1aa845f
--- /dev/null
+++ b/irdb-lib/plugins_install/zipr.sh
@@ -0,0 +1,7 @@
+#/bin/bash 
+
+cloneid=$1
+shift
+other_opts="$@"
+
+(set -x ; LD_LIBRARY_PATH=$LD_LIBRARY_PATH:$ZIPR_INSTALL/lib $ZIPR_INSTALL/bin/zipr.exe --variant $cloneid --zipr:objcopy $PS_OBJCOPY $other_opts)
diff --git a/irdb-lib/rida/SConscript b/irdb-lib/rida/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..68e393c43bea056f94b6b613ee43700032cb6b6b
--- /dev/null
+++ b/irdb-lib/rida/SConscript
@@ -0,0 +1,32 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+cpppath=''' 
+	 $SECURITY_TRANSFORMS_HOME/include 
+	 $SECURITY_TRANSFORMS_HOME/libehp/include 
+	 $SECURITY_TRANSFORMS_HOME/libEXEIO/include 
+	 $SECURITY_TRANSFORMS_HOME/libcapstone/include 
+	'''
+
+
+files=Glob( Dir('.').srcnode().abspath+"/*.cpp")
+
+
+pgm="rida.exe"
+
+LIBPATH=Split('''
+	$SECURITY_TRANSFORMS_HOME/lib 
+	$SECURITY_TRANSFORMS_HOME/libcapstone
+	''')
+LIBS=Split("ehp EXEIO pebliss capstone") 
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+pgm=myenv.Program(pgm,  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install/", pgm)
+Default(install)
+
+Return('install')
diff --git a/irdb-lib/rida/SConstruct b/irdb-lib/rida/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..9c9d2a5d563079f60954e46d422025a7c18edb82
--- /dev/null
+++ b/irdb-lib/rida/SConstruct
@@ -0,0 +1,12 @@
+
+
+
+env=Environment()
+
+env.Append(CFLAGS="    -g -Wall -Werror -std=c++11 -fmax-errors=2")
+env.Append(CXXFLAGS="  -g -Wall -Werror -std=c++11 -fmax-errors=2")
+env.Append(LINKFLAGS=" -g -Wall -Werror -std=c++11 -fmax-errors=2")
+
+Export('env')
+install=SConscript("SConscript")
+Return('install')
diff --git a/irdb-lib/rida/rida.cpp b/irdb-lib/rida/rida.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..91833dfb11270b5bd8f1a98f657d3fb5223054bf
--- /dev/null
+++ b/irdb-lib/rida/rida.cpp
@@ -0,0 +1,606 @@
+#include <iostream>
+#include <sstream>
+#include <assert.h>
+#include <set>
+#include <algorithm>
+#include <getopt.h>
+#include <ehp.hpp>
+#include <exeio.h>
+#include <string>
+#include "capstone/capstone.h"
+#include <fstream>
+#include <elf.h>
+#include <functional>
+
+
+using namespace std;
+using namespace EHP;
+using namespace EXEIO;
+
+#define ALLOF(a) begin(a),end(a)
+
+void usage(int argc, char* argv[])
+{
+	cout<<"Usage: "<<argv[0]<<" input.exe output.annot>"<<endl;
+	exit(1);
+}
+
+
+
+class CreateFunctions_t
+{
+	private:
+		shared_ptr<const EHFrameParser_t> ehp;
+		using Address_t = uint64_t;
+		class Range_t : public pair<Address_t,Address_t>
+		{
+			public:
+				Range_t(const Address_t &a, const Address_t &b) : pair<Address_t,Address_t>(a,b) { } 
+				bool contains(const Address_t &c) const { return first <= c && c<second; }
+			
+		};
+		using RangeSet_t = set<Range_t>;
+		set < RangeSet_t > sccs;
+		map<RangeSet_t,string> funcNames;
+		bool verbose;
+		exeio_t exeio;
+		csh cshandle;
+		ofstream outfile;
+		execlass_t file_class;
+		MachineType_t machine_type;
+		friend ostream& operator<<(ostream& os, const CreateFunctions_t::RangeSet_t& rs);
+	public:
+		CreateFunctions_t(const string &input_pgm, const string &output_annot, const bool p_verbose)
+			: 
+			verbose(p_verbose),
+			exeio(input_pgm),
+			cshandle(),
+			file_class(exeio.get_class()),
+			machine_type(exeio.getMachineType())
+		{
+			outfile.open(output_annot.c_str(), ofstream::out);
+			if(!outfile.is_open())
+			{
+				cerr<<"Cannot open "<<output_annot<<endl;
+				exit(1);
+			}
+			ehp = EHFrameParser_t::factory(input_pgm);
+			if(verbose)
+				ehp->print();
+
+			if(file_class!=ELF64 && file_class != ELF32)
+			{
+				cerr<<"Rida can only process ELF files."<<endl;
+				exit(1);
+			}
+
+			const auto cs_mode= 
+				machine_type==mtAarch64 ? CS_MODE_LITTLE_ENDIAN :
+				file_class==ELF64 ? CS_MODE_64 : 
+				file_class==ELF32 ? CS_MODE_32 : 
+				throw std::runtime_error("Cannot handle ELF class");
+
+			const auto my_cs_arch = 
+				machine_type == mtX86_64  ?  CS_ARCH_X86 : 
+				machine_type == mtI386    ?  CS_ARCH_X86 :
+				machine_type == mtAarch64 ?  CS_ARCH_ARM64 : 
+				throw std::runtime_error("Cannot handle architecture");
+
+			if (cs_open(my_cs_arch, cs_mode , &cshandle) != CS_ERR_OK)
+			{
+				cerr<<"Cannot initialize capstone"<<endl;
+				exit(1);
+			}
+		}
+		virtual ~CreateFunctions_t()
+		{
+			cs_close(&cshandle);
+		}
+
+
+		void calculate()
+		{
+
+
+			ehframeToSccs();
+			addSectionToSccs(".init");
+			addSectionToSccs(".fini");
+	
+			if(file_class==ELF64)
+			{
+				class Extracter64
+				{
+					public:
+						Elf64_Xword  elf_r_sym (Elf64_Xword a) { return ELF64_R_SYM (a); }
+						Elf64_Xword  elf_r_type(Elf64_Xword a) { return ELF64_R_TYPE(a); }
+						unsigned char  elf_st_bind(unsigned char a) { return ELF64_ST_BIND(a); }
+						unsigned char  elf_st_type(unsigned char a) { return ELF64_ST_TYPE(a); }
+				};
+				pltSplit<Elf64_Sym, Elf64_Rela, Elf64_Rel, Extracter64>(".plt", ".plt.got");
+				nameFunctions<Elf64_Sym, Extracter64>();
+			}
+			else
+			{
+				class Extracter32
+				{
+					public:
+						Elf32_Word  elf_r_sym (Elf32_Word a) { return ELF32_R_SYM (a); }
+						Elf32_Word  elf_r_type(Elf32_Word a) { return ELF32_R_TYPE(a); }
+						unsigned char  elf_st_bind(unsigned char a) { return ELF32_ST_BIND(a); }
+						unsigned char  elf_st_type(unsigned char a) { return ELF32_ST_TYPE(a); }
+				};
+				pltSplit<Elf32_Sym, Elf32_Rela, Elf32_Rel, Extracter32>(".plt", ".plt.got");
+				nameFunctions<Elf32_Sym, Extracter32>();
+			}
+
+		}
+
+		template<class T_Sym, class T_Extracter>
+		void nameFunctions()
+		{
+			// do symbol names.
+			parseSyms<T_Sym, T_Extracter>(".dynsym", ".dynstr");
+			parseSyms<T_Sym, T_Extracter>(".symtab", ".strtab");
+
+			auto namedFunctions=0U;
+			auto unnamedFunctions=0U;
+			auto functions=0U;
+
+			// set default names 
+			for(const auto &func: sccs)
+			{
+				assert(func.begin() != func.end());
+				const auto first_range=*(func.begin());
+				const auto startAddr=first_range.first;
+				std::stringstream ss;
+				ss << "sub_" << hex << startAddr;
+				const auto name = ss.str();
+
+				functions++;
+				if(funcNames[func]=="")	// destructive test OK, next line sets if empty.
+				{
+					unnamedFunctions++;
+					funcNames[func]=name;
+				}
+				else
+				{
+					namedFunctions++;
+				}
+					
+			}
+
+			cout<<"#ATTRIBUTE functions="<<dec<<functions<<endl;
+			cout<<"#ATTRIBUTE named_functions="<<dec<<namedFunctions<<endl;
+			cout<<"#ATTRIBUTE uunamed_functions="<<dec<<unnamedFunctions<<endl;
+	
+		}
+
+		template<class T_Sym, class T_Extracter>
+		void parseSyms(const string& secName, const string & stringSecName)
+		{
+			const auto sec=exeio.sections[secName];
+			if(!sec) return;	// err check
+
+			const auto stringSec=exeio.sections[stringSecName];
+			if(!stringSec) return; // err check
+
+			const auto data=sec->get_data();
+			const auto stringData=stringSec->get_data();
+
+			for(auto i=0U; i+sizeof(T_Sym) <= (size_t)sec->get_size(); i+=sizeof(T_Sym))
+			{
+				const auto sym=reinterpret_cast<const T_Sym *>(data+i);
+				const auto value=sym->st_value;
+				if(value==0) 
+					continue;
+
+				// works for both ELF64 and ELF32, macros defined the same.
+				const auto type=T_Extracter().elf_st_type(sym->st_info);
+				if(type!=STT_FUNC) 
+					continue;
+
+
+				// functions with non-zero address at this point.
+				const auto name_offset=sym->st_name;
+	
+				// sanity check string length
+				if(name_offset < 0U || name_offset > (size_t)stringSec->get_size())
+					continue;
+
+				// get the name
+				const auto name=string(stringData+name_offset);
+		
+
+				// find a function 
+				auto func_it=find_if(ALLOF(sccs), [&](const RangeSet_t& s) 
+					{ 
+						return s.begin() -> first == value;
+					});
+				if(func_it!=sccs.end())
+				{
+					cout<<"Setting function at "<<hex<<value<<" to name "<<name<<endl;
+					funcNames[*func_it]=name;
+				}
+
+			}
+		}
+
+		void ehframeToSccs()
+		{
+			const auto fdes=ehp->getFDEs();
+			for(const auto fde : *fdes) 
+				//sccs.insert({ RangeSet_t({fde->getStartAddress(), fde->getEndAddress()})});
+				sccs.insert(RangeSet_t({Range_t(fde->getStartAddress(),fde->getEndAddress())}));
+
+			cout<<hex;
+			if(getenv("SELF_VALIDATE"))
+				assert(fdes->size()>0);
+
+			for(const auto fde : *fdes)
+			{
+				if(verbose)
+					cout<<"Found FDE at : " << fde->getStartAddress() << "-"<<fde->getEndAddress()<<endl;
+				auto pair=Range_t(fde->getStartAddress(), fde->getEndAddress());
+				const auto lsda=fde->getLSDA();
+				assert(lsda);
+				const auto callsites=lsda->getCallSites();
+				assert(callsites);
+
+				for(const auto cs : *callsites)
+				{
+					if(verbose)
+						cout<<"\tCall site (0x"<<cs->getCallSiteAddress()<<"-"<<cs->getCallSiteEndAddress()
+						    <<") with landing pad=0x"<<cs->getLandingPadAddress()<<endl;
+					if(cs->getLandingPadAddress()==0x0)
+						continue;
+					auto set1_it=find_if(ALLOF(sccs), [&](const RangeSet_t& s) { return s.find(pair) != s.end(); } );
+					assert(set1_it!=sccs.end());
+
+					auto set2_it=find_if(ALLOF(sccs), [&](const RangeSet_t& s) 
+						{ 
+							return find_if(ALLOF(s), [&](const Range_t& r) { return r.contains(cs->getLandingPadAddress()); }) != s.end(); 
+						});
+					assert(set2_it!=sccs.end());
+					auto set1=*set1_it;
+					auto set2=*set2_it;
+					if(set1!=set2)
+					{
+						sccs.erase(set1);
+						sccs.erase(set2);
+						auto set3=RangeSet_t();
+						if(verbose)
+							cout<<"\tMerging: set1="<< hex<< set1 << " and set2="<<set2<<dec<<endl;
+						set_union(ALLOF(set1), ALLOF(set2), inserter(set3, set3.begin()));
+						sccs.insert(set3);
+					}
+				}
+			}
+
+
+		}
+
+		void addSectionToSccs(const string &sec_name)
+		{
+			const auto sec=exeio.sections[sec_name];
+			if(sec==nullptr)
+				return;
+			const auto range=Range_t(sec->get_address(), sec->get_address()+sec->get_size());
+			const auto ranges=RangeSet_t({range});
+			sccs.insert(ranges);
+		}
+
+		template<class T_Sym, class T_Rela, class T_Rel, class T_Extracter>
+		void pltSplit(const string &pltSecName, const string &endSecName)
+		{
+			const auto dynsymSec=exeio.sections[".dynsym"];
+			const auto dynstrSec=exeio.sections[".dynstr"];
+			const auto relapltSec=exeio.sections[".rela.plt"];
+			const auto relpltSec=exeio.sections[".rel.plt"];
+			const auto relSec=relapltSec  ? relapltSec : relpltSec;
+			const auto relSecEntrySize=relapltSec  ? sizeof(T_Rela) : sizeof(T_Rel);
+			
+
+			const auto addRange=[&](const Address_t s, size_t len)
+			{
+				if(verbose)
+					cout<<"Adding PLT function "<<s<<" "<<len<<endl;
+				sccs.insert(RangeSet_t({Range_t({s,s+len})}));
+			};
+
+			const auto addName=[&](const Address_t addr, uint64_t symIndex)
+			{
+				if(!dynsymSec) return;
+				if(!dynstrSec) return;
+				if(!relSec) return;
+			
+				// get the data out of the plt section.
+				const auto relData=relSec->get_data();
+				if(symIndex*relSecEntrySize >= (size_t)relSec->get_size()) return;
+				const auto relDataAsSymPtr=reinterpret_cast<const T_Rel *>(relData + symIndex*relSecEntrySize);
+				const auto &relEntry=*relDataAsSymPtr;
+
+				// calculate index into dynsym, section.
+				const auto dynsymIndex=T_Extracter().elf_r_sym(relEntry.r_info);
+				const auto dynsymData=dynsymSec->get_data();
+				const auto dynstrData=dynstrSec->get_data();
+
+				cout<<dec<<"At entry "<<symIndex<<", reloc entry has dynsym index "<<dynsymIndex<<endl;
+
+				// the index into the .dynsym section for the relocation.
+				const auto dynsymDataAsSymPtr=reinterpret_cast<const T_Sym *>(dynsymData);
+				if(dynsymIndex*sizeof(T_Sym) >= (size_t)dynsymSec->get_size()) return;
+
+				// get a reference to the dynsym entry.
+				const auto &dynsymEntry=dynsymDataAsSymPtr[dynsymIndex];
+				// extra where in the string table the name is.
+				const auto name_offset=dynsymEntry.st_name;
+				
+				// sanity check string length
+				if(name_offset < 0U || name_offset > (size_t)dynstrSec->get_size())
+					return;
+
+				const auto applyName=[&](const string& part, const Address_t myAddr)
+					{
+						// get the name
+						const auto name=string(dynstrData+name_offset)+part+"@plt";
+
+						// find a function 
+						auto func_it=find_if(ALLOF(sccs), [&](const RangeSet_t& s) 
+							{ 
+								return s.begin() -> first == myAddr;
+							});
+						if(func_it!=sccs.end())
+						{
+							cout<<"Setting function at "<<hex<<myAddr<<" to name "<<name<<endl;
+							funcNames[*func_it]=name;
+						}
+					};
+
+				applyName("part1", addr);
+				applyName("part2", addr+6);
+			};
+
+			const auto pltSec=exeio.sections[pltSecName];
+			if(pltSec==NULL) return;
+
+			const auto startAddr=pltSec->get_address();
+			const auto endAddr=pltSec->get_address()+pltSec->get_size();
+
+			if(verbose)
+				cout<<"Found plt function range is "<<hex<<startAddr<<"-"<<endAddr<<endl;
+
+			const auto pltRange_it=find_if(ALLOF(sccs), [&](const RangeSet_t& s) 
+				{ 
+					return find_if(ALLOF(s), [&](const Range_t& r) { return r.contains(startAddr); }) != s.end(); 
+				});
+			// erase startAddr if found.
+			if(pltRange_it!=sccs.end())
+				sccs.erase(pltRange_it);	// invalidates all iterators
+
+			auto dynsymEntryIndex=0;
+
+			const auto handle_x86_plt=[&]()
+			{
+				const auto plt_skip=16;
+				const auto plt_header_size=12;
+				const auto plt_entry_size=16;
+				const auto plt_entry_size_first_part=6;
+
+				addRange(startAddr,plt_header_size);
+				for(auto i=startAddr+plt_skip; i<endAddr; i+=plt_skip) 
+				{
+					addRange(i,plt_entry_size_first_part);
+					addRange(i+6,plt_entry_size-plt_entry_size_first_part);
+					addName(i,dynsymEntryIndex++);
+				}
+			};
+			const auto handle_arm_plt=[&]()
+			{
+				const auto plt_entry_size=16;
+				const auto plt_header_size=8*4;
+
+				addRange(startAddr,plt_header_size);
+				for(auto i=startAddr+plt_header_size; i<endAddr; i+=plt_entry_size) 
+				{
+					addRange(i,plt_entry_size);
+					addName(i,dynsymEntryIndex++);
+				}
+			};
+
+			switch(machine_type)
+			{
+				case mtX86_64:
+				case mtI386: 
+					handle_x86_plt();
+					break;
+				case mtAarch64:
+					handle_arm_plt();
+					break;
+				default:
+					assert(0);
+
+			};
+			cout<<"#ATTRIBUTE plt_entries="<<dec<<dynsymEntryIndex<<endl;
+
+
+			// deal with gotPlt Section.
+			const auto gotPltSec=exeio.sections[endSecName];
+			if(gotPltSec==NULL)
+				return;
+
+			// both 32- and 64-bit, entries are 6 bytes, with 2 bytes of padding.
+			const auto gotPltEntrySize=8;
+			const auto gotPltRangeSize=6;
+			const auto gotPltStartAddr=gotPltSec->get_address();
+			auto gotpltEntries=0U;
+
+			for(auto i=0U; i + gotPltRangeSize < (size_t)gotPltSec->get_size(); i+=gotPltEntrySize)
+			{
+				addRange(gotPltStartAddr+i,gotPltRangeSize);
+				gotpltEntries++;
+			}
+			cout<<"#ATTRIBUTE gotplt_entries="<<dec<<gotpltEntries<<endl;
+	
+		}
+
+		void doBelongTos(const Range_t &range, const Address_t startAddr)
+		{
+			const auto sec=exeio.sections.findByAddress(range.first);
+			assert(sec);
+			const auto secEnd=exeio.sections.findByAddress(range.second-1);
+			assert(sec==secEnd);	 // same section.
+			const auto data=sec->get_data();
+			const auto secStartAddr=sec->get_address();
+			const auto range_len=range.second-range.first;
+			const auto the_code=(const uint8_t*)(data+(range.first-secStartAddr));
+
+			auto insn=(cs_insn *)nullptr;
+
+			const auto count = cs_disasm(cshandle, the_code, range_len, range.first, 0, &insn);
+			if (count > 0) 
+			{
+				for (auto j = 0U; j < count; j++) 
+				{
+					outfile<<hex<<"\t"<<insn[j].address<<"\t"<<dec<<insn[j].size<<"\tINSTR BELONGTO\t"<<hex<<startAddr<< "\t; "<<insn[j].mnemonic << " " << insn[j].op_str<<endl;
+				}
+
+				cs_free(insn, count);
+			} 
+			else
+			{
+				cerr<<"ERROR: Failed to disassemble code at "<<range.first<<"-"<<range.second<<endl;
+				exit(1);
+			}
+
+
+		}
+		void doBelongTos(const RangeSet_t &scc)
+		{
+			const auto min=*scc.begin();
+			const auto startAddr=min.first;
+
+			for(auto range : scc)
+				doBelongTos(range,startAddr);
+
+		}
+
+		void writeAnnotations()
+		{
+			cout<<"The functions are:"<<endl;
+			auto i=0;
+			for(const auto &scc : sccs)
+			{
+				const auto min=*scc.begin();
+				const auto max=*prev(scc.end());
+				const auto size=max.second-min.first;
+		
+				cout<<"Function "<<dec<<i++<<" (" <<funcNames[scc] << ") is "<<hex<<min.first<<" "<<dec<<max.second-min.first<<endl;
+				const auto usefp=getUseFp(scc);
+
+				outfile<<hex<<"\t"<<min.first<<"\t"<<dec<<size<<"\tFUNC GLOBAL\t"<<funcNames[scc]<<" "<< usefp << endl;
+				doBelongTos(scc);
+			}
+			if(getenv("SELF_VALIDATE"))
+				assert(sccs.size()>0);
+		}
+
+		string getUseFp(const RangeSet_t scc)
+		{
+			assert(scc.begin()!=scc.end());
+			const auto startAddr=scc.begin()->first;
+			const auto fde=ehp->findFDE(startAddr);
+			if(!fde) return "NOFP";
+			const auto &ehprogram=fde->getProgram();
+			const auto ehprogramInstructions=ehprogram.getInstructions();
+
+			const auto def_cfa_rbp_it = find_if(ALLOF(*ehprogramInstructions), [&](const shared_ptr<EHProgramInstruction_t> insn)
+				{
+					assert(insn);
+					const auto &insnBytes=insn->getBytes();
+					// 0xd, 0x5 is "def_cfa_register ebp" 
+					// 0xd, 0x6 is "def_cfa_register rbp" 
+					const auto reg=file_class==ELF64 ? (uint8_t)0x6 : (uint8_t)0x5;
+					return insnBytes==EHProgramInstructionByteVector_t({(uint8_t)0xd, reg });
+				});
+			return def_cfa_rbp_it == ehprogramInstructions->end() ?  "NOFP" : "USEFP";
+		}
+		
+
+
+};
+
+ostream& operator<<(ostream& os, const CreateFunctions_t::RangeSet_t& rs)
+{
+	for(const auto r : rs)
+	{
+		os<<"("<<r.first<<"-"<<r.second<<"), ";
+	}
+	return os;
+}
+
+int main(int argc, char* argv[])
+{
+
+        if(argc < 3)
+        {
+		usage(argc,argv);
+                exit(1);
+        }
+        // Parse some options for the transform
+        const static struct option long_options[] = {
+                {"verbose", no_argument, 0, 'v'},
+                {"help", no_argument, 0, 'h'},
+                {"usage", no_argument, 0, '?'},
+                {0,0,0,0}
+        };
+        auto short_opts="vh?";
+        auto verbose=false;
+	auto index = (int)0;
+        while(1) 
+	{
+                int c = getopt_long(argc, argv,short_opts, long_options, &index);
+                if(c == -1)
+                        break;
+                switch(c) 
+		{
+                        case 0:
+                                break;
+                        case 'v':
+				verbose=true;
+                                break;
+                        case '?':
+                        case 'h':
+                                usage(argc,argv);
+                                exit(1);
+                                break;
+                        default:
+                                break;
+                }
+        }
+
+
+	if(optind+2 > argc)
+	{
+		usage(argc,argv);	
+		exit(1);
+	}
+
+	auto input_pgm=string(argv[optind]);
+	auto output_annot=string(argv[optind+1]);
+	for(auto i=optind+2 ; i < argc; i++)
+	{
+		ofstream out(argv[i]);	// touch file
+		if(!out.is_open())
+		{
+			cerr<<"Cannot touch file "<<argv[i]<<endl;
+			exit(1);
+		}
+		
+	}
+
+	CreateFunctions_t create_funcs(input_pgm,output_annot,verbose);
+	create_funcs.calculate();
+	create_funcs.writeAnnotations();
+
+	return 0;
+}
diff --git a/irdb-lib/thanos/SConscript b/irdb-lib/thanos/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..ed7ad18ccbdec2248fb96d7f5fcef85375cac017
--- /dev/null
+++ b/irdb-lib/thanos/SConscript
@@ -0,0 +1,32 @@
+import os
+
+
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+cpppath=''' 
+	 $IRDB_SDK/include 
+	 $SECURITY_TRANSFORMS_HOME/libIRDB-core/include 
+	'''
+
+
+files=Glob( Dir('.').srcnode().abspath+"/*.cpp")
+
+myenv.Append(CXXFLAGS = " -std=c++11 -Wall ")
+
+pgm="thanos.exe"
+
+LIBPATH="$SECURITY_TRANSFORMS_HOME/lib"
+LIBS=Split( env.subst('$BASE_IRDB_LIBS')+ " irdb-transform dl") 
+myenv=myenv.Clone(CPPPATH=Split(cpppath))
+pgm=myenv.Program(pgm,  files,  LIBPATH=LIBPATH, LIBS=LIBS)
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/plugins_install", pgm)
+Default(install)
+
+	
+	
+
+ret=[]+install
+Return('ret')
diff --git a/irdb-lib/thanos/SConstruct b/irdb-lib/thanos/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..44d3bd9e81dfb9812806072103183b71c0810436
--- /dev/null
+++ b/irdb-lib/thanos/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+ret=SConscript("SConscript")
+Return('ret')
diff --git a/irdb-lib/thanos/thanos.cpp b/irdb-lib/thanos/thanos.cpp
new file mode 100644
index 0000000000000000000000000000000000000000..e336c3307ff9e4ab7a1e3387c74943f9c3fea7fe
--- /dev/null
+++ b/irdb-lib/thanos/thanos.cpp
@@ -0,0 +1,435 @@
+#include <irdb-core>
+#include <libIRDB-core.hpp>
+#include <dlfcn.h> 
+#include <vector>
+#include <memory>
+#include <sstream>
+#include <iostream>
+#include <iomanip>
+#include <unistd.h>
+#include <fcntl.h>
+#include <fstream>
+#include <ctime>
+#include <ext/stdio_filebuf.h>
+
+
+
+using namespace std;
+using namespace IRDB_SDK;
+
+#define ALLOF(a) begin(a),end(a)
+
+// global to be used like cout/cerr for writing to the logs
+int thanos_log_fd=-1;
+ostream *thanos_log;
+ostream *real_cout;
+ostream *real_cerr;
+string thanos_path;
+bool redirect_opt=true;
+int new_stdout_fd=1;
+int new_stderr_fd=2;
+
+class ThanosPlugin_t
+{
+    public:
+        static unique_ptr<ThanosPlugin_t> pluginFactory(const string plugin_details);
+	static int saveChanges();
+	bool isOptional()
+	{
+		return step_optional;
+	}
+	string getStepName()
+	{
+		return step_name;
+	}
+	int runPlugin();
+
+    private:
+        // methods
+        ThanosPlugin_t(const string p_step_name,
+                       const bool p_step_optional,
+                       const vector<string> p_step_args
+                       )
+                       :
+                           step_name(p_step_name),
+                           step_optional(p_step_optional),
+                           step_args(p_step_args)
+                       {
+                       }
+	void tidyIR();
+	int executeStep(TransformStep_t& the_step, const bool are_debugging);
+	int commitAll();
+
+        // data
+        const string step_name;
+        const bool step_optional;
+        const vector<string> step_args;
+	static const unique_ptr<IRDBObjects_t> shared_objects;
+};
+// initialize private static data member
+const unique_ptr<IRDBObjects_t> ThanosPlugin_t::shared_objects(new libIRDB::IRDBObjects_t());
+
+using PluginList_t = vector<unique_ptr<ThanosPlugin_t>>;
+PluginList_t getPlugins(const int argc, char const *const argv[]); 
+
+int main(int argc, char* argv[])
+{
+	thanos_path=argv[0];
+
+	new_stdout_fd=dup(STDOUT_FILENO);
+	new_stderr_fd=dup(STDERR_FILENO);
+
+	__gnu_cxx::stdio_filebuf<char> stdout_filebuf(new_stdout_fd, ios::out); 
+	__gnu_cxx::stdio_filebuf<char> stderr_filebuf(new_stderr_fd, ios::out); 
+	
+	ostream my_real_cout(&stderr_filebuf);
+	ostream my_real_cerr(&stdout_filebuf);
+        real_cout=&my_real_cout;
+        real_cerr=&my_real_cerr;
+
+	auto thanos_log_fileptr=fopen("logs/thanos.log", "a+");
+	if(!thanos_log_fileptr)
+	{
+		*real_cerr<<"Cannot open logs/thanos.log"<<endl;
+		exit(1);
+	}
+	thanos_log_fd=fileno(thanos_log_fileptr);
+	__gnu_cxx::stdio_filebuf<char> thanos_log_filebuf(thanos_log_fd, ios::out); 
+	ostream thanos_log_stream(&thanos_log_filebuf);
+ 	thanos_log=&thanos_log_stream;
+
+	// make sure stuff goes to the log unless otherwise indicated by using real_cout
+	dup2(thanos_log_fd, STDOUT_FILENO);
+	dup2(thanos_log_fd, STDERR_FILENO);
+
+	// get plugins
+	auto argv_iter=1;
+	while (true)
+	{
+		if(argv_iter >= argc)
+		{
+			break;
+		}
+		if(string(argv[argv_iter])=="--no-redirect")
+		{
+			redirect_opt=false;
+			argv_iter++;
+		}
+		else
+			break;
+	}
+	const auto plugin_argv_iter=argv_iter;
+
+	auto thanos_plugins = getPlugins(argc-plugin_argv_iter, argv+plugin_argv_iter);	
+	if(thanos_plugins.size() == 0)
+	{
+		// for now, usage is pretty strict to enable simple
+		// parsing, because this program is only used by an
+		// automated script
+		*thanos_log << "Syntax error in arguments." << endl;
+		*thanos_log << "USAGE: <thanos opts> (\"<step name> [-optional] [--step-args [ARGS]]\")+" << endl;
+		return 1;
+	}
+
+	for(unsigned int i = 0; i < thanos_plugins.size(); ++i)
+	{
+		ThanosPlugin_t* plugin = thanos_plugins[i].get();
+
+		const int result = plugin->runPlugin();
+		// if that returns failure AND the step is not optional
+		if(result != 0 && !plugin->isOptional())
+		{
+			*thanos_log << "A critical step failed: " << plugin->getStepName() << endl;
+			*thanos_log << "If DEBUG_STEPS is not on, this failure could "
+			     << "be due to an earlier critical step." << endl;	 
+			return 1; // critical step failed, abort
+		}
+	}
+	// write back final changes
+	const int result = ThanosPlugin_t::saveChanges();
+	if(result != 0)
+	{
+		*thanos_log << "A critical step failed: " << (thanos_plugins.back())->getStepName() 
+		     << endl;
+                *thanos_log << "If DEBUG_STEPS is not on, this failure could "
+                     << "be due to an earlier critical step." << endl;
+                return 1; // critical step failed, abort
+	}
+	else
+	{
+		return 0; // success :)
+	}
+}
+
+
+PluginList_t getPlugins(const int argc, char const *const argv[])
+{	
+	PluginList_t plugins;
+	
+	for(auto i = 0; i < argc; ++i)
+	{
+		auto the_plugin = ThanosPlugin_t::pluginFactory(string(argv[i]));	
+		if(the_plugin == nullptr)
+			return PluginList_t();
+		plugins.push_back(move(the_plugin));
+	}
+	return plugins;
+}
+
+
+// assumes that tokens are always space-separated
+// (cannot be delineated by quotes, for example)
+const vector<string> getTokens(const string arg_string)
+{
+	vector<string> tokens;
+	istringstream arg_stream(arg_string);
+    	string token; 
+    	while (getline(arg_stream, token, ' ')) 
+	{
+               	tokens.push_back(token);
+    	}
+	return tokens;
+}
+
+
+unique_ptr<ThanosPlugin_t> ThanosPlugin_t::pluginFactory(const string plugin_details)
+{
+	auto tokens = getTokens(plugin_details);
+	if(tokens.size() < 1)
+		return unique_ptr<ThanosPlugin_t>(nullptr);
+
+	const auto step_name = tokens[0];
+	auto step_optional = false;
+	vector<string> step_args;
+	for(unsigned int i = 1; i < tokens.size(); ++i)
+	{
+		if(tokens[i] == "--step-args")
+		{
+			if(tokens.begin()+i+1 < tokens.end())
+				step_args.assign(tokens.begin()+i+1, tokens.end());
+			break;
+		}
+		else if(tokens[i] == "-optional")
+		{
+			step_optional = true;
+		}
+		else
+		{
+			return unique_ptr<ThanosPlugin_t>(nullptr);
+		}
+	}	
+	return unique_ptr<ThanosPlugin_t>(new ThanosPlugin_t(step_name, step_optional, step_args));	
+}
+
+
+int ThanosPlugin_t::runPlugin()
+{
+	static const char *const base_path = getenv("SECURITY_TRANSFORMS_HOME");
+        if(base_path == NULL)
+        {
+		*thanos_log << "Environment variables not set." << endl;
+		return -1;
+    	}
+    	static const auto plugin_path (string(base_path).append("/plugins_install/"));
+
+	void *const dlhdl = dlopen((plugin_path+"lib"+step_name+".so").c_str(), RTLD_NOW);
+        if(dlhdl == NULL)
+        {
+        	const auto err=dlerror();
+                *thanos_log<<"Cannot open "<<step_name<<": "<<err<<endl;
+		return -1;
+        }
+        
+       	const void *const sym = dlsym(dlhdl, "getTransformStep"); 
+        if(sym == NULL)
+        {
+        	const auto err=dlerror();
+                *thanos_log<<"Cannot find getTransformStep in "<<step_name<<": "<<err<<endl;
+		return -1;
+        }
+
+	using GetTransformPtr_t = shared_ptr<TransformStep_t> (*)(void);  // function pointer, takes void, returns TransformStep_t shared ptr
+	GetTransformPtr_t func=(GetTransformPtr_t)sym;
+	shared_ptr<TransformStep_t> the_step = (*func)();
+	assert(the_step != NULL);
+	
+	static const char *const are_debugging = getenv("DEBUG_STEPS");
+
+	auto logfile=(FILE*)nullptr;
+
+	auto are_logging = !((bool) are_debugging);
+	if(are_logging)
+	{
+		// setup logging
+		auto logfile_path = "./logs/"+step_name+".log";
+		logfile=fopen(logfile_path.c_str(), "a+");
+		if(!logfile)
+		{
+			*real_cout<<"Cannot open log file "<<logfile_path<<endl;
+			exit(1);
+		}
+		if(redirect_opt)
+		{
+			dup2(fileno(logfile), STDOUT_FILENO);
+			dup2(fileno(logfile), STDERR_FILENO);
+		}
+		else
+		{
+			dup2(new_stdout_fd, STDOUT_FILENO);
+			dup2(new_stderr_fd, STDERR_FILENO);
+		}
+	}
+	
+
+	const auto start_time = clock();
+  	const auto start_t=time(nullptr);
+	const auto start_time_str = ctime(&start_t);
+
+	const auto step_result = executeStep(*(the_step.get()), (bool) are_debugging);
+
+        const auto end_time = clock();
+  	const auto end_t=time(nullptr);
+	const auto end_time_str = ctime(&end_t);
+        const auto elapsed_time = (double)(end_time-start_time)/ CLOCKS_PER_SEC;
+
+        cout<< "#ATTRIBUTE start_time=" << start_time_str ; // endl in time_str
+        cout<< "#ATTRIBUTE end_time="   << end_time_str   ; // endl in time_str
+        cout<< "#ATTRIBUTE elapsed_time="  << elapsed_time<<endl;
+        cout<< "#ATTRIBUTE step_name=" << step_name<<endl;
+        cout<< "#ATTRIBUTE step_command=  " << thanos_path << " \"" << step_name 
+	    << " --step-args "; copy(ALLOF(step_args), ostream_iterator<string>(cout, " ")); cout<<"\""<<endl;
+        cout<< "#ATTRIBUTE step_exitcode="<<dec<<step_result<<endl;
+
+
+	dup2(thanos_log_fd, STDOUT_FILENO);
+	dup2(thanos_log_fd, STDERR_FILENO);
+	if(logfile)
+		fclose(logfile);
+
+	the_step.reset(); // explicitly get rid of the handle to the library so we can close it.
+	dlclose(dlhdl);
+
+	// return status of execute method
+	return step_result; 
+}
+
+
+void ThanosPlugin_t::tidyIR()
+{
+	optind=1;
+	shared_objects->tidyIR();
+}
+
+int ThanosPlugin_t::executeStep(TransformStep_t& the_step, const bool are_debugging)
+{
+
+	*real_cout<<"Performing step "<<the_step.getStepName()<< " [dependencies=unknown] ..."; // no endl intentionally.
+	flush(*real_cout);
+
+
+	tidyIR();
+
+	const int parse_retval = the_step.parseArgs(step_args);
+	if(parse_retval != 0)
+	{
+		*real_cout<<"Done.  Command failed! ***************************************"<<endl;
+		if(!step_optional)
+		{
+			*real_cout<<"ERROR: The "<<the_step.getStepName()<<" step is necessary, but options parsing failed.  Exiting early."<<endl;	
+		}
+		return parse_retval;
+	}
+
+	pqxxDB_t* pqxx_interface = shared_objects->getDBInterface();
+	if(step_optional)
+	{
+		const int error = shared_objects->writeBackAll(thanos_log);
+		if(error)
+		{
+			return 1; // the failure must be from a critical step, abort
+		}
+		else
+		{
+		    // commit changes (in case this step fails) and reset interface
+		    pqxx_interface->commit();
+		    pqxx_interface = shared_objects->resetDBInterface();
+		}
+	}
+
+	const int step_error = the_step.executeStep(shared_objects.get());
+
+	if(step_error)
+	{
+		if(step_optional)
+		{
+
+                        *real_cout<<"Done.  Command failed! ***************************************"<<endl;
+			// delete all shared items without writing
+			// next step will have to get the last "good" version from DB
+			shared_objects->deleteAll();
+		}
+		else
+		{
+                        *real_cout<<"Done.  Command failed! ***************************************"<<endl;
+                        *real_cout<<"ERROR: The "<<the_step.getStepName()<<" step is necessary, but failed.  Exiting early."<<endl;
+			return 1; // critical step failed, abort
+		}
+	}
+	else
+	{
+			*real_cout<<"Done.  Successful."<<endl;
+	}
+
+	if(step_optional)
+	{
+		// write changes to DB to see if it succeeds
+		const int error = shared_objects->writeBackAll(thanos_log);
+		if(error)
+		{
+			// abort changes by resetting DB interface
+			pqxx_interface = shared_objects->resetDBInterface();
+		}
+		else if(are_debugging)
+		{
+			// commit changes (in case next step fails) and reset interface 
+			pqxx_interface->commit();
+			pqxx_interface = shared_objects->resetDBInterface();
+		}
+	}
+	else if(are_debugging)
+	{
+		// write changes to DB in case next step fails
+		const int error = shared_objects->writeBackAll(thanos_log);
+		if(error)
+		{
+			return 1; // critical step failed, abort
+		}
+		else
+		{
+			// commit changes (in case next step fails) and reset interface 
+			pqxx_interface->commit();
+			pqxx_interface = shared_objects->resetDBInterface();
+		}
+	}
+
+	return step_error;	
+}
+
+
+int ThanosPlugin_t::saveChanges()
+{
+	pqxxDB_t* pqxx_interface = shared_objects->getDBInterface();
+        const int error = shared_objects->writeBackAll(thanos_log);
+        if(error)
+        {
+        	return 1; // critical step failed, abort
+        }
+        else
+        {
+        	// commit changes and reset interface 
+        	pqxx_interface->commit();
+        	pqxx_interface = shared_objects->resetDBInterface();
+       		return 0;
+        }
+}
+
diff --git a/irdb-lib/third_party/LICENSE.txt b/irdb-lib/third_party/LICENSE.txt
new file mode 100644
index 0000000000000000000000000000000000000000..42d3e128c3508710e668d7631a54a5f0bd36fce1
--- /dev/null
+++ b/irdb-lib/third_party/LICENSE.txt
@@ -0,0 +1 @@
+Software under this directory and sub-directory is subject to its own licensing requirement 
diff --git a/irdb-lib/xform/SConscript b/irdb-lib/xform/SConscript
new file mode 100644
index 0000000000000000000000000000000000000000..e1af37fa9cd25ac1e18962acd38edb281d8f18b1
--- /dev/null
+++ b/irdb-lib/xform/SConscript
@@ -0,0 +1,39 @@
+import os
+
+Import('env')
+myenv=env.Clone()
+myenv.Replace(SECURITY_TRANSFORMS_HOME=os.environ['SECURITY_TRANSFORMS_HOME'])
+
+lib="xform"
+
+files=  '''
+	instruction_descriptor.cpp
+	function_descriptor.cpp
+	elfreader.cpp
+	null_transform.cpp
+	rewriter.cpp
+	spri_alloc.c
+	gen_hash.c
+	constant_hash.c
+	funclist_hash.c
+	instrmap_hash.c
+	framerestore_hash.c
+	stackref_hash.c
+	'''
+cpppath=''' 
+	$SECURITY_TRANSFORMS_HOME/libIRDB/include/
+	$SECURITY_TRANSFORMS_HOME/libEXEIO/include/
+	$SECURITY_TRANSFORMS_HOME/include/
+	'''
+
+CFLAGS="-fPIC  -DUBUNTU"
+
+myenv=myenv.Clone(CC="$CXX", CPPPATH=Split(cpppath), CFLAGS=CFLAGS)
+myenv.Append(CXXFLAGS=" -std=c++11 ")
+lib=myenv.SharedLibrary(lib, Split(files), LIBS=Split("IRDB-core EXEIO"), LIBPATH=Split("$SECURITY_TRANSFORMS_HOME/lib"))
+
+install=myenv.Install("$SECURITY_TRANSFORMS_HOME/lib/", lib)
+
+Default(install)
+
+Return('lib')
diff --git a/irdb-lib/xform/SConstruct b/irdb-lib/xform/SConstruct
new file mode 100644
index 0000000000000000000000000000000000000000..e542bcbc14c04dc8cdf8e3535b9585b4ef0cf232
--- /dev/null
+++ b/irdb-lib/xform/SConstruct
@@ -0,0 +1,7 @@
+
+
+
+env=Environment()
+Export('env')
+lib=SConscript("SConscript")
+Return(lib)
diff --git a/libcapstone b/libcapstone
new file mode 160000
index 0000000000000000000000000000000000000000..9408c0de4f3a4b2a3cc1cac3f22219301c561400
--- /dev/null
+++ b/libcapstone
@@ -0,0 +1 @@
+Subproject commit 9408c0de4f3a4b2a3cc1cac3f22219301c561400
diff --git a/libehp b/libehp
new file mode 160000
index 0000000000000000000000000000000000000000..cda036f54b68d2eb1bfd0c0d636dad954433a3b7
--- /dev/null
+++ b/libehp
@@ -0,0 +1 @@
+Subproject commit cda036f54b68d2eb1bfd0c0d636dad954433a3b7
diff --git a/third_party/elfio-code b/third_party/elfio-code
new file mode 160000
index 0000000000000000000000000000000000000000..9f9407d3018fb4317e56bb78a74b9cdbf6c96306
--- /dev/null
+++ b/third_party/elfio-code
@@ -0,0 +1 @@
+Subproject commit 9f9407d3018fb4317e56bb78a74b9cdbf6c96306