A program used to analyze the DLL file format in Linux

Source: Internet
Author: User

/*
The following code can be run in either Linux or windows.
Why is this Code retained?
1. including the analysis of the PE file format in the recent period;
In the future, if you need to use the PE format, you just need to look at this code and it is easy to get started.
2. The conversion from RVA to file offset in the PE file is relatively large;
This Code provides better function implementation.
The function of this program is to determine whether a file is a. Cpl file. The CPL file is actually a DLL, but contains a special interface.
*/
# Include <stdlib. h>
# Include <stdio. h>
# Include <memory. h>
# Include <string>
# Include <vector>
Using namespace STD;
// The following structure defines the PE file header in winnt. h.
Typedef struct _ image_data_directory {
Unsigned long virtualaddress;
Unsigned long size;
} Image_data_directory, * pimage_data_directory;
Typedef struct _ image_file_header {
Unsigned short machine;
Unsigned short numberofsections;
Unsigned long timedatestamp;
Unsigned long pointertosymboltable;
Unsigned long numberofsymbols;
Unsigned short sizeofoptionalheader;
Unsigned short characteristics;
} Image_file_header, * pimage_file_header;
Typedef struct _ image_optional_header {
//
// Standard fields.
//
 
Unsigned short magic;
Char majorlinkerversion;
Char minorlinkerversion;
Unsigned long sizeofcode;
Unsigned long sizeofinitializeddata;
Unsigned long sizeofuninitializeddata;
Unsigned long addressofentrypoint;
Unsigned long baseofcode;
Unsigned long baseofdata;
 
//
// Nt additional fields.
//
 
Unsigned long imagebase;
Unsigned long sectionalignment;
Unsigned long filealignment;
Unsigned short majoroperatingsystemversion;
Unsigned short minoroperatingsystemversion;
Unsigned short majorimageversion;
Unsigned short minorimageversion;
Unsigned short majorsubsystemversion;
Unsigned short minorsubsystemversion;
Unsigned long win32versionvalue;
Unsigned long sizeofimage;
Unsigned long sizeofheaders;
Unsigned long checksum;
Unsigned short subsystem;
Unsigned short dllcharacteristics;
Unsigned long sizeofstackreserve;
Unsigned long sizeofstackcommit;
Unsigned long sizeofheapreserve;
Unsigned long sizeofheapcommit;
Unsigned long loaderflags;
Unsigned long numberofrvaandsizes;
Image_data_directory datadirectory [16];
} Image_optional_header32, * pimage_optional_header32;
Typedef struct _ image_nt_headers {
Unsigned long signature;
Image_file_header fileheader;
Image_optional_header32 optionalheader;
} Image_nt_headers32, * pimage_nt_headers32;
Typedef pimage_nt_headers32 pimage_nt_headers;
Typedef struct _ image_section_header {
Char name [8];
Union {
Unsigned long physicaladdress;
Unsigned long virtualsize;
} MISC;
Unsigned long virtualaddress;
Unsigned long sizeofrawdata;
Unsigned long pointertorawdata;
Unsigned long pointertorelocations;
Unsigned long pointertolinenumbers;
Unsigned short numberofrelocations;
Unsigned short numberoflinenumbers;
Unsigned long characteristics;
} Image_section_header, * pimage_section_header;
Typedef image_nt_headers32 image_nt_headers;
// This Code determines which section of RVA is in.
Pimage_section_header imagerva2section (pimage_nt_headers, unsigned long dwrva)
{
Int I;
Pimage_section_header = (pimage_section_header) (char *) (pimage_nt_headers) + sizeof (image_nt_headers ));
For (I = 0; I <pimage_nt_headers-> fileheader. numberofsections; I ++ ){
// Pimage_section_header-> virtualaddress is the first address of the Section.
// Pimage_section_header-> sizeofrawdata is the section length.
If (pimage_section_header-> virtualaddress) & (dwrva <= (pimage_section_header-> virtualaddress + pimage_section_header-> sizeofrawdata )))
Return (pimage_section_header );
Pimage_section_header ++;
}
Return (null );
}
/*
What is the principle of calculating the offset?
First, determine the section in which RVA is located, and then check the section table to find the Section
File offset. Use the following formula to calculate the file offset:
Offset = RVA-(Section virtual memory address-section File offset)
*/
Unsigned long rva2offset (char * praw, unsigned long dwrva)
{
Unsigned long _ offset;
Pimage_section_header section;
Pimage_nt_headers;
 
Pimage_nt_headers = (pimage_nt_headers) (praw );
Section = imagerva2section (pimage_nt_headers, dwrva );
If (Section = NULL)
Return (-1 );
// Section-> virtualaddress is the virtual memory address of the Section.
// Section-> pointertorawdata is the file offset of the Section.
_ Offset = dwrva + section-> pointertorawdata-section-> virtualaddress;
Return (_ offset );
}
// In fact the. Cpl file is a. dll file, so we want to check if it has "cplapplet" symbol.
Bool _ iscpl (File * PF)
{
If (null = PF)
Return false;
 
Char symbolbuff [10];
Unsigned long dwoffset = 0;
Unsigned short magicnumber = 0;
 
Fseek (PF, 0, seek_set );
Fread (symbolbuff, 1, 2, Pf );
 
If (symbolbuff [0]! = 'M' | symbolbuff [1]! = 'Z ')
Return false;
 
// Skip Dos Stub.
// PE file header is a Dos Stub
Fseek (PF, 60, seek_set );
 
// Read PE offset.
// The Real PE file header is saved at an offset.
Fread (& dwoffset, 1, sizeof (dwoffset), Pf );
 
// Read nt header.
// Read the file header and save it to a structure
Fseek (PF, dwoffset, seek_set );
Char ntheader [10240];
Fread (ntheader, 1, sizeof (ntheader), Pf );
Fseek (PF, dwoffset, seek_set );
 
// Judge PE signature.
// The header of the PE file header is a PE signature.
Fread (symbolbuff, 1, 2, Pf );
If (symbolbuff [0]! = 'P' | symbolbuff [1]! = 'E ')
Return false;
 
// Read magic number to determine if the file is pe32 or pe32 +.
Fseek (PF, 22, seek_cur );
Fread (& magicnumber, 1, sizeof (magicnumber), Pf );
 
// Get the offset of optional Header Data Directories
Dwoffset = 0;
If (0x10b = magicnumber)
Dwoffset = 96-2;
Else
Dwoffset = 112-2;
 
Fseek (PF, dwoffset, seek_cur );
Fread (& dwoffset, 1, sizeof (dwoffset), Pf );
 
// Seek to optional Header Data Directories
Dwoffset = rva2offset (ntheader, dwoffset );
If (dwoffset =-1)
Return false;
Fseek (PF, dwoffset, seek_set );
 
Int atenum = 0; // The number of entries in the export address table.
Int nnpnum = 0; // The number of entries in the Name Pointer table. This is also the number of entries in the ordinal table.
 
Fseek (PF, dwoffset + 20, seek_set );
Fread (& atenum, 1, sizeof (atenum), Pf );
 
Fseek (PF, dwoffset + 24, seek_set );
Fread (& nnpnum, 1, sizeof (nnpnum), Pf );
 
// Skip the export address table.
Fseek (PF, dwoffset + 40 + 4 * atenum, seek_set );
 
// Now process name table.
Vector <int> vecstraddr;
For (INT I = 0; I <nnpnum; ++ I ){
Int nnpaddr = 0;
Fread (& nnpaddr, 1, sizeof (nnpaddr), Pf );

Nnpaddr = rva2offset (ntheader, nnpaddr );
If (nnpaddr =-1)
Continue;

Vecstraddr. push_back (nnpaddr );
}
// Compare name string.
For (I = 0; I <vecstraddr. Size (); ++ I ){
Char buffstr [128];
Int straddr = vecstraddr [I];

Fseek (PF, straddr, seek_set );
Fread (buffstr, 1, sizeof (buffstr), Pf );

If (strcmp (buffstr, "cplapplet") = 0)
Return true;
}
 
Return false;
}
Bool iscpl (const char * inputfile)
{
File * pF = fopen (inputfile, "rb ");
Bool res = _ iscpl (PF );
Fclose (PF );
 
Return res;

}

Int main (INT argc, char * argv [])
{
Bool res = iscpl ("C: \ test. Cpl ");
 
Return 0;
}

This article is reproduced from:

Http://tassardge.blog.163.com/blog/static/1723017082008102185122256/

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.