|
|
||
|
|
||
|
|
||
Now, consider the problem of writing programs equally translatable by both MASM and TASM. Conditional assembling is suited to this purpose. The most
Listing 12.1
Listing 12.1: Using conventional assembling to develop a compatible program
|
|
.586P
; Flat memory model
.MODEL FLAT, STDCALL
; Check whether the MASM symbolic constant is defined
IFDEF MASM
; Work with MASM
EXTERN ExitProcess@4:NEAR
EXTERN MessageBoxA@16:NEAR
includelib c:\masm32\lib\kernel32.lib
includelib c:\masm32\lib\user32.lib
ELSE
; Work with TASM
EXTERN ExitProcess:NEAR
EXTERN MessageBoxA:NEAR
includelib c:\tasm32\lib\import32.lib
ExitProcess@4 = ExitProcess
MessageBoxA@16 = MessageBoxA
ENDIF
;------------------------------------------------
; Data segment
_DATA SEGMENT
MSG DB "An easy program", 0
TIT DB "Title", 0
_DATA ENDS
; Code segment
_TEXT SEGMENT
START:
PUSH 0
PUSH OFFSET TIT
PUSH OFFSET MSG
PUSH 0 ; Screen descriptor
CALL MessageBoxA@16
;--------------------------------------
PUSH 0
CALL ExitProcess@4
_TEXT ENDS
END START
|
|
To translate the program using MASM, use the following:
ML /c /coff /DMASM PROG.ASM
LINK /SUBSYSTEM:WINDOWS PROG.OBJ
To translate the same program using TASM, use the following:
TASM32 /ml PROG.ASM
TLINK32 -aa PROG.OBJ
As you can see, everything is reduced to checking whether the MASM symbolic constant is defined (the
/DMASM
command-line option). Another problem is adding the
@N
suffix. You bypass this problem by using the
=
operator, with which the
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
|
|
||
Because of the importance of the
CreateFile
function, I decided to
Windows operates with the concept of devices. This approach allows it to unify the processes of obtaining and transmitting information, which means that the same API functions are used for data
|
Device
|
Explanation |
|---|---|
|
Pipes |
There are two types of pipes: named and anonymous. Named pipes are used for connecting the source and destination through the local area network. Anonymous pipes play the same role within the limits of the same computer. |
|
Directories |
Directories exist as the structural units of file systems. Direct information exchange with a directory can change its attributes (e.g., the file compression attribute for the directory contents). |
|
Communications resources |
|
|
Console |
Text screen and information input/output into the text screen. |
|
Logical |
This type includes hard disk partitions and floppy
|
|
Mailslots |
This allows the transmission of information from several sources to the same destination within the limits of a single computer, a local area network, or domain. |
|
Sockets |
Sockets are devices that exchange information between two computers supporting the sockets mechanism. |
|
Files |
These devices permanently store large
|
|
Physical |
These provide access to hard disk structures (e.g., a partition table or structures residing on a partition). |
Now, having
In this section, you will consider this function in the file management context. Because the first argument of the
CreateFile
function is the fully qualified filename (the
For creating a filename, the
The
The . character designates the current directory, and .. stands for the parent directory. Additionally, the last . character in the string separates the filename from the filename extension used by the operating system for recognizing the file type.
Symbols such as <, >, : ,/, , and \ are invalid for filenames and directory
Names of devices (e.g., aux , con , and prn ) cannot be used as filenames.
A fully qualified filename must be represented by a zero-
Functions that use filenames as parameters are insensitive to the case of English characters.
Reserved keywords such as CLOCK$ , NUL , COM1 , and LPT1 cannot be used as names of files or directories.
| Note |
All devices listed in Table 13.1 are representatives of the kernel objects class. To be more precise, they become kernel objects after they are created using
CreateFile
or any similar function (thus, the
CreateFile
name reflects the essence of the problem). Structures describing objects are stored in the kernel area, which means that they are protected against access by
|
Now, it is time to consider the parameters accepted by the CreateFile function.
First parameter Address of the string containing the filename.
Second parameter Defines how the data will be exchanged with this device.
The following values are possible:
It is assumed that there will be no data read or write operations. Only file parameters will be changed (time characteristics, attributes, etc.).
GENERIC_READ = 80000000h Data read from the file is expected.
GENERIC_WRITE = 40000000h Data write into the file is expected.
GENERIC_READ GENERIC_WRITE This combination allows data read and data write operations.
Additionally, this parameter can contain several flags that specify access rights to this file (or to another device). All of these flags are listed in the documentation but are rarely used. For example, the DELETE = l0000h value specifies that the file (object) can be deleted.
Third parameter This parameter specifies the type of access to the file. To be more precise, this parameter specifies the desired access, because in practice the file or object access can be limited because the required object might already be opened by another process. The possible values of this parameter are as
Other processes cannot have exclusive access to this file. If the file is already opened by another process, this value of the parameter won't allow you to
FILE_SHARE_READ = 1
This setting enables
FILE_SHARE_WRITE = 2 This setting enables subsequent open operations on the object to request write access. Otherwise, other processes cannot open the object if they request write access.
FILE_SHARE_WRITE FILE_SHARE_READ This value allows subsequent open operations on the object to request read and write access. The operation will fail only if another process has already opened this object in exclusive mode.
FILE_SHARE_DELETE = 4 This allows other processes to access the object and delete it.
Fourth parameter This parameter points to a special structure called SECURITY_ATTRIBUTES . This structure allows you to specify security information and determine whether the descriptor returned by the CreateFile function must be inherited. Most frequently, this parameter is set to NULL . This means that the descriptor is not inherited. Consider the SECURITY_ATTRIBUTES structure:
SECURITY_ATTRIBUTES STRUC
L DD ?
DESC DD ?
INHER DD ?
SECURITY_ATTRIBUTES ENDS
As you can see, the structure includes only three fields. The first field determines the length of the entire structure; in this case, it must be 12 bytes. The second field is the inheritable descriptor. The third field takes the values 0 or 1. If the field value is 1, then all child processes will inherit the descriptor.
Fifth parameter This parameter defines the behavior of the CreateFile function if the file lacks the specified name.
CREATE_NEW = 1 This parameter instructs the system to create a new file if the file with the specified name is missing; otherwise, the function doesn't execute.
CREATE_ALWAYS = 2 This parameter instructs the system to create the file in any case. If the file with the specified name exists, it will be overwritten.
OPEN_EXISTING = 3 This setting instructs the system to open the file with the specified name if it exists.
OPEN_ALWAYS = 4 This parameter instructs the system to open the file if it exists, or to create a new file if the file with the specified name is missing.
TRUNCATE_EXISTING = 5
This parameter instructs the system to open the existing file and reset its
Sixth parameter This parameter is mainly used for defining the attributes of the file being created (the attribute list was provided in Chapter 11). Additionally, here you can specify flags that allow the system to optimize caching algorithms. There are also other flags, the values of which are as follows:
FILE_FLAG_NO_BUFFERING = 20000000h The file must be accessed without data buffering.
FILE_FLAG_SEQUENTIAL_SCAN = 8000000h If this flag is set, the system assumes that the file is accessed sequentially. Accordingly, the maximum reading rate can be achieved with sequential reading.
FILE_FLAG_RANDOM_ACCESS = l0000000h This flag is used for indicating that the system must not read large volumes of redundant data. It should be used if frequent searching in the file is expected.
FILE_FLAG_WRITE_THROUGH = 80000000h This flag disables write-through caching when writing into a file. In this case, all changes are written immediately to the disk.
FILE_FLAG_DELETE_ON_CLOSE = 4000000h If this flag is set, then the operating system will delete this file after all its descriptors are closed.
FILE_FLAG_BACKUP_SEMANTICS = 2000000h This flag is used in backup software.
FILE_FLAG_POSIX_SEMANTICS = l000000h This instructs the system to take into account the case of characters when creating or opening a file.
FILE_FLAG_OPEN_REPARSE_POINT = 200000h
This flag instructs the system to ignore the presence of the
FILE_FLAG_OPEN_NO_RECALL = l00000h If this flag is set, the system doesn't restore the file from remote storage (see Chapter 11).
FILE_FLAG_OVERLAPED = 4000000Oh This flag sets asynchronous data exchange with the device. This topic will be covered later in this chapter.
Seventh parameter This parameter can contain the descriptor of a file already opened. When the file that already exists is opened, the attributes defined by this parameter are used. Usually this parameter is set to NULL .
If the function fails, it returns the INVALID_HANDLE_VALUE = ˆ 1 .
|
|
||
|
|
||
|
|
||