• R/O
  • SSH
  • HTTPS

peframework: Commit


Commit MetaInfo

Revision3 (tree)
Time2017-04-11 21:12:29
Authorquiret

Log Message

- added resource helpers
- added import helpers
- improved a few things about resources

Change Summary

Incremental Difference

--- include/peloader.h (revision 2)
+++ include/peloader.h (revision 3)
@@ -1450,6 +1450,8 @@
14501450
14511451 static void AllocatePEImportFunctionsData( PESection& writeSect, functions_t& functionList );
14521452
1453+ static functions_t CreateEquivalentImportsList( const functions_t& right );
1454+
14531455 functions_t funcs;
14541456 std::string DLLName;
14551457
@@ -1465,7 +1467,7 @@
14651467 PESectionAllocation importsAllocEntry;
14661468
14671469 // Resource information.
1468- struct PEResourceItem
1470+ struct PEResourceItem abstract
14691471 {
14701472 enum class eType
14711473 {
@@ -1473,10 +1475,11 @@
14731475 DATA
14741476 };
14751477
1476- inline PEResourceItem( eType typeDesc, std::u16string name ) : itemType( typeDesc ), name( std::move( name ) )
1478+ inline PEResourceItem( eType typeDesc, bool isIdentifierName, std::u16string name, std::uint16_t identifier )
1479+ : itemType( std::move( typeDesc ) ),
1480+ hasIdentifierName( std::move( isIdentifierName ) ), name( std::move( name ) ), identifier( std::move( identifier ) )
14771481 {
1478- this->identifier = 0;
1479- this->hasIdentifierName = false;
1482+ return;
14801483 }
14811484
14821485 virtual ~PEResourceItem( void )
@@ -1484,6 +1487,9 @@
14841487 return;
14851488 }
14861489
1490+ // Helpers.
1491+ std::wstring GetName( void ) const;
1492+
14871493 eType itemType;
14881494 std::u16string name; // valid if hasIdentifierName == false
14891495 std::uint16_t identifier; // valid if hasIdentifierName == true
@@ -1490,11 +1496,11 @@
14901496 bool hasIdentifierName; // if true then identifier field is valid, name is not
14911497 };
14921498
1493- struct PEResourceInfo : PEResourceItem
1499+ struct PEResourceInfo : public PEResourceItem
14941500 {
1495- inline PEResourceInfo( std::u16string name, PESection *dataSect, std::uint32_t dataOff, std::uint32_t dataSize )
1496- : PEResourceItem( eType::DATA, std::move( name ) ),
1497- sectRef( dataSect, dataOff, dataSize )
1501+ inline PEResourceInfo( bool isIdentifierName, std::u16string name, std::uint16_t identifier, PESectionDataReference dataRef )
1502+ : PEResourceItem( eType::DATA, std::move( isIdentifierName ), std::move( name ), std::move( identifier ) ),
1503+ sectRef( std::move( dataRef ) )
14981504 {
14991505 this->codePage = 0;
15001506 this->reserved = 0;
@@ -1507,9 +1513,10 @@
15071513 std::uint32_t reserved;
15081514 };
15091515
1510- struct PEResourceDir : PEResourceItem
1516+ struct PEResourceDir : public PEResourceItem
15111517 {
1512- inline PEResourceDir( std::u16string name ) : PEResourceItem( eType::DIRECTORY, std::move( name ) )
1518+ inline PEResourceDir( bool isIdentifierName, std::u16string name, std::uint16_t identifier )
1519+ : PEResourceItem( eType::DIRECTORY, std::move( isIdentifierName ), std::move( name ), std::move( identifier ) )
15131520 {
15141521 this->characteristics = 0;
15151522 this->timeDateStamp = 0;
@@ -1535,6 +1542,11 @@
15351542 inline PEResourceDir& operator = ( const PEResourceDir& right ) = delete;
15361543 inline PEResourceDir& operator = ( PEResourceDir&& right ) = default;
15371544
1545+ // Helper API.
1546+ PEResourceItem* FindItem( bool isIdentifierName, const std::u16string& name, std::uint16_t identifier );
1547+
1548+ bool RemoveItem( const PEResourceItem *theItem );
1549+
15381550 std::uint32_t characteristics;
15391551 std::uint32_t timeDateStamp;
15401552 std::uint16_t majorVersion;
--- src/peloader.cpp (revision 2)
+++ src/peloader.cpp (revision 3)
@@ -2,7 +2,7 @@
22
33 #include "peloader.internal.hxx"
44
5-PEFile::PEFile( void ) : resourceRoot( std::u16string() ), sections( 0x1000, 0x10000 )
5+PEFile::PEFile( void ) : resourceRoot( false, std::u16string(), 0 ), sections( 0x1000, 0x10000 )
66 {
77 // By default we generate plain PE32+ files.
88 // If true then PE32+ files are generated.
--- src/peloader.imports.cpp (revision 2)
+++ src/peloader.imports.cpp (revision 3)
@@ -70,4 +70,25 @@
7070 }
7171
7272 return funcOut;
73+}
74+
75+PEFile::PEImportDesc::functions_t PEFile::PEImportDesc::CreateEquivalentImportsList( const functions_t& funcs )
76+{
77+ PEImportDesc::functions_t newFuncs;
78+
79+ size_t modImpCount = funcs.size();
80+
81+ for ( size_t n = 0; n < modImpCount; n++ )
82+ {
83+ const PEFile::PEImportDesc::importFunc& impFunc = funcs[ n ];
84+
85+ PEFile::PEImportDesc::importFunc carbonCopy;
86+ carbonCopy.isOrdinalImport = impFunc.isOrdinalImport;
87+ carbonCopy.name = impFunc.name;
88+ carbonCopy.ordinal_hint = impFunc.ordinal_hint;
89+
90+ newFuncs.push_back( std::move( carbonCopy ) );
91+ }
92+
93+ return newFuncs;
7394 }
\ No newline at end of file
--- src/peloader.read.cpp (revision 2)
+++ src/peloader.read.cpp (revision 3)
@@ -1102,13 +1102,16 @@
11021102 }
11031103
11041104 // * Resources.
1105- PEResourceDir resourceRoot = std::u16string(); // very weird assignment here, but required; call the constructor.
1105+ PEResourceDir resourceRoot( false, std::u16string(), 0 );
11061106 {
11071107 struct helpers
11081108 {
1109- inline static PEResourceDir LoadResourceDirectory( PESectionMan& sections, PEDataStream& rootStream, std::u16string nameOfDir, const PEStructures::IMAGE_RESOURCE_DIRECTORY& serResDir )
1109+ inline static PEResourceDir LoadResourceDirectory(
1110+ PESectionMan& sections, PEDataStream& rootStream,
1111+ bool isIdentifierName, std::u16string nameOfDir, std::uint16_t identifier,
1112+ const PEStructures::IMAGE_RESOURCE_DIRECTORY& serResDir )
11101113 {
1111- PEResourceDir curDir( std::move( nameOfDir ) );
1114+ PEResourceDir curDir( std::move( isIdentifierName ), std::move( nameOfDir ), std::move( identifier ) );
11121115
11131116 // Store general details.
11141117 curDir.characteristics = serResDir.Characteristics;
@@ -1122,7 +1125,7 @@
11221125 std::uint16_t numIDEntries = serResDir.NumberOfIdEntries;
11231126
11241127 // Function to read the data behind a resource directory entry.
1125- auto resDataParser = [&]( std::u16string nameOfItem, const PEStructures::IMAGE_RESOURCE_DIRECTORY_ENTRY& entry ) -> PEResourceItem*
1128+ auto resDataParser = [&]( bool isIdentifierName, std::u16string nameOfItem, std::uint16_t identifier, const PEStructures::IMAGE_RESOURCE_DIRECTORY_ENTRY& entry ) -> PEResourceItem*
11261129 {
11271130 // Seek to this data entry.
11281131 rootStream.Seek( entry.OffsetToData );
@@ -1134,11 +1137,13 @@
11341137 PEStructures::IMAGE_RESOURCE_DIRECTORY subDirData;
11351138 rootStream.Read( &subDirData, sizeof(subDirData) );
11361139
1137- PEResourceDir subDir = LoadResourceDirectory( sections, rootStream, std::move( nameOfItem ), subDirData );
1140+ PEResourceDir subDir = LoadResourceDirectory(
1141+ sections, rootStream,
1142+ std::move( isIdentifierName ), std::move( nameOfItem ), std::move( identifier ),
1143+ subDirData
1144+ );
11381145
1139- PEResourceDir *subDirItem = new PEResourceDir( std::move( subDir ) );
1140-
1141- return subDirItem;
1146+ return new PEResourceDir( std::move( subDir ) );
11421147 }
11431148 else
11441149 {
@@ -1164,15 +1169,13 @@
11641169
11651170 // We dont have to recurse anymore.
11661171 PEResourceInfo resItem(
1167- std::move( nameOfItem ),
1168- dataSect, std::move( sectOff ), itemData.Size
1172+ std::move( isIdentifierName ), std::move( nameOfItem ), std::move( identifier ),
1173+ PESectionDataReference( dataSect, std::move( sectOff ), itemData.Size )
11691174 );
11701175 resItem.codePage = itemData.CodePage;
11711176 resItem.reserved = itemData.Reserved;
11721177
1173- PEResourceInfo *resItemPtr = new PEResourceInfo( std::move( resItem ) );
1174-
1175- return resItemPtr;
1178+ return new PEResourceInfo( std::move( resItem ) );
11761179 }
11771180 };
11781181
@@ -1210,10 +1213,8 @@
12101213 }
12111214
12121215 // Create a resource item.
1213- PEResourceItem *resItem = resDataParser( std::move( nameOfItem ), namedEntry );
1216+ PEResourceItem *resItem = resDataParser( false, std::move( nameOfItem ), 0, namedEntry );
12141217
1215- resItem->hasIdentifierName = false;
1216-
12171218 // Store ourselves.
12181219 curDir.children.push_back( resItem );
12191220 }
@@ -1234,11 +1235,8 @@
12341235 }
12351236
12361237 // Create a resource item.
1237- PEResourceItem *resItem = resDataParser( std::u16string(), idEntry );
1238+ PEResourceItem *resItem = resDataParser( true, std::u16string(), idEntry.Id, idEntry );
12381239
1239- resItem->identifier = idEntry.Id;
1240- resItem->hasIdentifierName = true;
1241-
12421240 // Store it.
12431241 curDir.children.push_back( resItem );
12441242 }
@@ -1270,7 +1268,11 @@
12701268 PEStructures::IMAGE_RESOURCE_DIRECTORY resDir;
12711269 resDataStream.Read( &resDir, sizeof(resDir) );
12721270
1273- resourceRoot = helpers::LoadResourceDirectory( sections, resDataStream, std::u16string(), resDir );
1271+ resourceRoot = helpers::LoadResourceDirectory(
1272+ sections, resDataStream,
1273+ false, std::u16string(), 0,
1274+ resDir
1275+ );
12741276 }
12751277 }
12761278
--- src/peloader.resource.cpp (nonexistent)
+++ src/peloader.resource.cpp (revision 3)
@@ -0,0 +1,57 @@
1+// Resource helper API.
2+#include "peloader.h"
3+
4+#include <sdk/UniChar.h>
5+
6+// Generic finder routine.
7+PEFile::PEResourceItem* PEFile::PEResourceDir::FindItem( bool isIdentifierName, const std::u16string& name, std::uint16_t identifier )
8+{
9+ for ( PEResourceItem *resItem : this->children )
10+ {
11+ if ( resItem->hasIdentifierName != isIdentifierName )
12+ continue;
13+
14+ if ( !isIdentifierName )
15+ {
16+ if ( resItem->name == name )
17+ return resItem;
18+ }
19+ else
20+ {
21+ if ( resItem->identifier == identifier )
22+ return resItem;
23+ }
24+ }
25+
26+ return NULL;
27+}
28+
29+std::wstring PEFile::PEResourceItem::GetName( void ) const
30+{
31+ if ( !this->hasIdentifierName )
32+ {
33+ return CharacterUtil::ConvertStrings <char16_t, wchar_t> ( this->name );
34+ }
35+ else
36+ {
37+ std::wstring charBuild( L"(ident:" );
38+
39+ charBuild += std::to_wstring( this->identifier );
40+
41+ charBuild += L")";
42+
43+ return charBuild;
44+ }
45+}
46+
47+bool PEFile::PEResourceDir::RemoveItem( const PEFile::PEResourceItem *theItem )
48+{
49+ auto findIter = std::find( this->children.begin(), this->children.end(), theItem );
50+
51+ if ( findIter == this->children.end() )
52+ return false;
53+
54+ this->children.erase( findIter );
55+
56+ return true;
57+}
\ No newline at end of file
Show on old repository browser