Arithmetic

Arithmetic Procedures
GetPercent
IntDiv
IntMul
IntSqrt


Array Functions

arr_add | Add an integer to every member of a DWORD array
arr_mul | Multiply every member of a DWORD array by an integer
arr_sub | Subtract an integer from every member of a DWORD array
create_array | Create an array of pointers to a user defined array


C Style Character Testing

isalpha
isalphanum
islower
isnumber
isupper


Clipboard Functions

GetClipboardText | Get text from clipboard.
SetClipboardText | Write text to clipboard.


Command Line

Command Line Procedures
ArgCL
ArgClC
GetCL
getcl_ex


Console Mode Functions

ClearScreen
locate
StdIn
StdOut
StripLF
StdErr
Clear screen and place cursor at start Set X Y location of cursor
Get input from console
Output text at current location
Strip CRLF from StdIn result
Output text to standard out.


Conversions

atodw
htodw
dwtoa
dw2hex
dw2ah
udw2str
ustr2dw
ltoa
atol
Convert ascii number to DWORD Convert HEX string to DWORD
Convert DWORD to ascii string
Convert DWORD to hex string
Convert DWORD to ascii hex
Convert unsigned DWORD to string
Convert string to unsigned DWORD
Convert signed DWORD to ascii string
Convert ascii string to signed DWORD


Custom Control

BmpButton


Encryption Components

Notes On Encryption
XorData
RolData
RorData


Extended Functions

This range of procedures are aimed at applications that must stream output data at very high speed. Where there is a matching normal procedure and the required conversion is not highly speed critical, it is a better choice for size efficiency reasons.

atodw_ex
byt2bin_ex
dw2bin_ex
dw2hex_ex
wrd2bin_ex
hexflip32
bin2byte_ex


File Functions

exist filesize
read_disk_file
write_disk_file
LoadList
Test if file exists Get the disk file size
Read disk file into buffer
Write disk file from buffer
Load files into a list box


Floating Point Conversions
StrToFloat
FloatToStr/2


Graphics Primitives

circle
line


Hex to Binary Conversions

bin2hex
hex2bin


Image Functions

DisplayBmp
DisplayIcon
VerticalTile
BitmapFromFile
BitmapFromResource
BitmapFromMemory


In Memory Text Read and Write

readline
writeline
tstline
parse_line


Memory Functions

Malloc
Free
MemCopy
memfill
CreateMMF
CloseMMF
cmpmem
Allocate memory by the iMalloc method Free memory allocated by the iMalloc method
Copy memory from one address to another
Fill memory with a specified 4 bytes
Create a memory mapped file
Close a memory mapped file
Compare two addresses of equal length


Misc

a2wc | Convert ANSI string to UNICODE string
shell | Run a program synchronously
shell_ex | Extended version with priority control
wshell | An alternative technique run a program synchronously
nrandom | Generate a random integer within a range
IPtoString | Convert a DWORD IP to string
StripRangeI | Inclusive strip characters between 2 supplied characters
StripRangeX | Exclusive strip characters between 2 supplied characters
testreg | Test if a zero terminated string is a register
AsciiDump | Dump any byte sequence to assembler DB format
HexDump | Convert any byte sequence to a hex dump
byte_count | Write the count of every byte in a source to an array
load_drives | Load a list box with drive and volume data


Obsolete String Functions

The following string function names have been remapped as follows in the MASM32.INC file. Code written with the obsolete name will work exactly as before with no modification required.

lnstr     equ <szLen>
cmpstr    equ <szCmp>
cmpsi     equ <szCmpi>
revstr    equ <szRev>
lcase     equ <szLower>
ucase     equ <szUpper>
ltrim     equ <szLtrim>
rtrim     equ <szRtrim>
trim      equ <szTrim>
lstr      equ <szLeft>
rstr      equ <szRight>
midstr    equ <szMid>


Parsing Functions

ArgByNumber | Optional streaming or single argument mode parser
readline | Read a single line of text from a zero terminated source
decomment | Strip comments from a single line of code
get_ml | Get next single or multiline statement with comments stripped
create_array | Create an array of user defined size and member count
parse_line | Tokenise source text and load into a string array
lfcnt | Return the number of line feeds in a zero terminated text


Path Functions

GetAppPath
NameFromPath
GetPathOnly


Pre-Built Dialogs

AboutBox
GetFile
GetIP
GetTextInput


Recommendations with string sorts

These are the component string sorting algorithms that were used in the development of the two main string sorting algorithms.
There are 7 string sorting algorithms presented here that are rated according to their usefulness. Some have been used for the two sorts above while others have been used in their development. They have been written and optimised by hand in assembler and the string comparison code has been written directly inline to maximise the speed of each algorithm. They are useful within the following described boundaries.

Speed
-----
1. Quick Sort
2. Shell Sort
3. CISORT
4. CCSORT
5. Comb Sort
6. Insertion sort
7. Bubble Sort

Flexibility
-----------
1. CISORT No known quadratic behaviour
2. CCSORT No known quadratic behaviour
3. Comb Sort No known quadratic behaviour
4. Shell Sort Only fails on low range large count data
5. Quick Sort Fails on ordered and low range data
6. Insertion sort Only suitable for preordered data
7. Bubble Sort Only suitable for preordered data

CISORT
CISORT is a hybrid COMB / INSERTION that utilises the highly predictable performance of a COMB sort preordering pass and the speed of an INSERTION sort on pre-ordered data. It has been designed to be a SAFE sort that can be used with general purpose data that is not pre-known in its ordering. It has no known orderings weaknesses that force it into quadratic behaviour on any tested form of data.

CCSORT
CCSORT is a hybrid COMB / COCKTAIL SHAKER sort that is faster than a COMB sort because of the bi-directional bubble sort addressing the problem of "turtles" but it is slower than the hybrib COMB / INSERTION sort. It has been designed to be a SAFE sort that can be used with general purpose data that is not pre-known in its ordering. It has no known orderings weaknesses that force it into quadratic behaviour on any tested form of data.

QUICK Sort
A QUICK sort is the fastest available sort for data that is randomly distributed. Its speed advantage over other classic designs justifies using it where the data is known to be randomly ordered. It will fail if the data is pre-ordered or if the range of data is very limited in relation to the member count to be sorted. It normally fails due to exceeding the available stack memory from excess recursion depth.

SHELL Sort
The variation presented is an Incerpi-Sedgewick Shell sort that uses a predefined gap table. While it is faster than other variants of a SHELL sort, it is not as fast as a QUICK sort but it is a lot more robust with pre-ordered or unusually ordered data. The only tested data format that will force it into quadratic behaviour is very low range repetitive data with a large member count.

COMB sort
A COMB sort is an O(n log n) time complexity sort that can be used for general purpose sorting. It is susceptable to data elements that are at the high end of the data in the direction of the sweep which take many operations to correctly place. These are commonly referred to as turtles.

INSERTION Sort
An INSERTION sort is too slow to use by itself but it has a very useful characteristic of being fast on near ordered data that makes it suitable to use with hybrid sorts. It is also very fast on small data counts which makes it useful for modifying other sorting algorithms.

BUBBLE sort
Except for very small member counts, a bubble sort is far too slow by itself to be useful.


Rich Edit Functions

RichEd1
RichEd2
Read_File_In
Write_To_Disk


Search Functions

InString
BinSearch
Boyer Moore Algorithms
WordCount
partial


Sorting Functions

Sorting Overview
Quick Sort
Comb Sort


String Sorting
assort proc arr:DWORD,cnt:DWORD,rdi:DWORD ; ascending version
dssort proc arr:DWORD,cnt:DWORD,rdi:DWORD ; descending version

Description
There are two master sorting algorithms presented here which are hybrids of different sorting technologies.

Parameters
1. arr The starting address of the array of string pointers.
2. cnt The number of members in the array of pointers.
3. rdi A recursion depth limiter.

Important
There must not be any NULL pointers in the array of pointers passed to any of the string sorting procedures as the string comparison code is not designed to handle this situation. The string comparisons occur at a critical speed related area in the sorting algorithms and to add the code to test for NULL pointers would incur a substantial performance penalty. A NULL pointer in this context is a string address that has ascii ZERO as its first character. If the array loading code is at risk of setting a pointer to a NULL value, it must be filtered to prevent this from happening.
The MASM32 library has a pair of tokenisers that can be used to load an array of pointers to either lines of text or individual words under the topic Tokenisers

Return Value
The return values are designed to give some useful feedback about the arrangement of the data being sorted. If EAX returns zero then the data was highly random in nature and was sorted by the quick sort component of the algorithm.

If the data is already sorted or near ordered or has unusual arrangements like a very high number of repetitions of a limited number of variations, it will exceed the preset recursion depth for the quick sort and will be finished by a hybrid comb / insertion sort.

Comments
There are three seperate sorting algorithms that can be used by the two master sorting procedures. The first level is a very high speed quick sort which is ideally suited for highly random data. If the data is already sorted or ordered in such a way that a quick sort will be too slow, it determines the decay by the recursion depth of the quick sort and switches over to another hybrid sort that is highly insensitive to data arrangement to finish off the sorting.

The second sort is a hybrid comb sort which has very predictable performance to preorder the data which is then passed to an insertion sort which is very fast on near ordered data.
The strategy is to maximise the performance for the most common data which is usually random in nature and switch over to the high safety version if the quick sort decays into quadratic behaviour.

The recursion depth setting is set to a default of 100 if the "rdi" parameter is set to zero, otherwise it can be set manually to whatever depth is required based on some knowledge of the arrangement of the data being sorted. If the quick sort reaches the depth set in the "rdi" parameter, it exits and returns a value indicating that it has failed due to recursion depth. This is the trigger to run the high safety sort if the quick sort fails.

The following string sorting algorithms were used in the development of the above two string sorts. Some are components of the main hybrid while others were part of the testing and development. With the exception of the bubble sort, most are useful within understood limitations.

All of the string sorts below have been manually optimised for speed and the critical string comparison code has been written inline to avoid the extra call and branch overhead from using an external procedure to perform the comparisons.

; --------------------------------------------------
; high speed quick sort with recursion depth limiter
; This algorithm is used by the above hybrid.
; --------------------------------------------------
asqsort PROTO :DWORD,:DWORD,:DWORD,:DWORD,:DWORD
dsqsort PROTO :DWORD,:DWORD,:DWORD,:DWORD,:DWORD

; -----------------------------------------------------
; comb / insertion sort hybrid used by the above hybrid.
; -----------------------------------------------------
; args are,
; 1. pointer array address
; 2. Member count. Do NOT correct for zero based index.

acisort PROTO :DWORD,:DWORD
dcisort PROTO :DWORD,:DWORD

; -----------------------------------
; insertion sort for the above hybrid
; -----------------------------------
; args are,
; 1. pointer array address
; 2. Member count. Do NOT correct for zero based index.

aissort PROTO :DWORD,:DWORD
dissort PROTO :DWORD,:DWORD

; ----------------------------------------------
; high safety margin comb / cocktail shaker sort
; ----------------------------------------------
; args are,
; 1. pointer array address
; 2. Member count. Do NOT correct for zero based index.

ccsorta PROTO :DWORD,:DWORD
ccsortd PROTO :DWORD,:DWORD

; ---------------------------------------------
; The following 3 string sort algorithms were
; used in the development of the above versions.
; Within some data format limitations, they are
; useful string sorting algorithms.
; 1. Quick sort is fast on random data but can
; fail due to recursion depth on some data formats.
; 2. Shell sort is more robust but can be forced
; into quadratic behaviour with deliberately
; structured data.
; 3. Comb sort is robust and reliable but both the
; CCSORT and CISORT are faster and more consistent.
; ---------------------------------------------
; Quick string sort
; -----------------
; args are,
; 1. pointer array address
; 2. ZERO as lower array index
; 3. Member count MINUS 1

qssorta PROTO :DWORD,:DWORD,:DWORD
qssortd PROTO :DWORD,:DWORD,:DWORD

; -----------------
; Shell string sort
; -----------------
; args are,
; 1. pointer array address
; 2. ZERO as lower array index
; 3. Member count MINUS 1

ssorta PROTO :DWORD,:DWORD,:DWORD
ssortd PROTO :DWORD,:DWORD,:DWORD

; ----------------
; Comb string sort
; ----------------
; args are,
; 1. pointer array address
; 2. Member count. Do NOT correct for zero based index.

cstsorta PROTO :DWORD,:DWORD
cstsortd PROTO :DWORD,:DWORD

; -----------------------
; traditional bubble sort
; -----------------------
; args are,
; 1. pointer array address
; 2. ZERO as lower array index
; 3. Member count MINUS 1

bstsorta PROTO :DWORD,:DWORD,:DWORD
bstsortd PROTO :DWORD,:DWORD,:DWORD

 Recommendations with string sorts


System Dialogs

BrowseForFolder
ColorDialog
FontDialog
PageSetupDialog
PrintDialog
OpenFileDialog
SaveFileDialog


Tokenisers

Two basic designs are presented here, one that tokenises words in a source file and the other that tokenises lines in a text file. Both forms are "in place" tokenisers which means they modify the input text data rather than allocate the extra memory and extra processing time to copy each token into a variable length string array.

The advantage of using an "in place" tokeniser is that it is much faster than the additional allocation and additional processor time copying the data on a token by token basis. Application can be as diverse as parsing a script, creating an array of pointers to words or lines of text for sorting or creating an "overkill" command line parser.

If modifying the original text data is a problem, you can copy the original data to another memory buffer and pass the memory buffer to either procedure.

ltok | Tokenise lines of text "in place" in a text file.
wtok | Tokenise words "in place" in a text file.


Unicode Common Dialogs

ucOpenFileDialog
ucSaveFileDialog


Unicode String Functions

NOTE that while many of these procedures are similar to their ASCII versions, there are differences in some procedures in terms of return values and mode of operation. You should check the documentation for each procedure to ensure that you use it as it was designed so that you get predictable results.

ucappend
ucArgByNum
ucCatStr
ucCmdTail
ucCmp
ucCopy
ucFind
ucGetCL
ucgetline
ucLeft
ucLen
ucLower
ucLtrim
ucMid
ucMonoSpace
ucMultiCat
ucRemove
ucRep
ucRev
ucRight
ucRtrim
ucUpper
ucWcnt


Window Framing Functions

Frame3D
FrameWindow
FrameCtrl
Fram eGrp
Low level framing procedure Draw frame around Window
Draw frame around a control
Frame a group of controls


sz String Functions

Zero Terminated String Functions

These procedures are for working with ascii/ansi zero terminated strings.

szappend | Append zero terminated string to buffer
szLen | Length of zero terminated string
szCopy | Copy zero terminated string
szCmp | Case sensitive string comparison
szCmpi | Case insensitive string comparison
Cmpi | Case insensitive comparison without length argument
szRev | Reverse characters in string
szLower | Convert string to lower case
szUpper | Convert string to upper case
szTrim | Left and right trim string
szLtrim | Left trim string
szRtrim | Right trim string
szCatStr | Concantenate two strings
szMultiCat | Concantenate multiple strings
szMonoSpace | Format a string with single spaces and trimmed ends
szLeft | Get a count of characters from left side of string
szRep | Replace text in a zero terminated string
szRight | Get a count of characters from right side of string
szRemove | Remove substring from source string
szMid | Get a count of characters from middle of string
StrLen | Agner Fog's DWORD string length procedure
InString | Find substring in zero terminated source string
wordreplace | Whole word replace
szWcnt | Count the occurrence of text in a zero terminated string


a2wc

a2wc proc asc_txt:DWORD

Description
Convert zero terminated ANSI string to UNICODE string

Parameters
1. asc_txt Address of zero terminated string in ANSI format

Return Value
The address of a memory buffer that contains the UNICODE string.

Comments
When the string is no longer required, the return address should be deallocated with the OLE function,

invoke SysFreeString,strhandle
or the MASM32 macro
free$ strhandle


AboutBox

AboutBox proc Parent :DWORD,Instance :DWORD,Icon:DWORD,
              appname :DWORD,description:DWORD,
              copyright:DWORD

Description
AboutBox is a prebuilt dialog that is designed to be used as the about box in an application. Additional information is displayed in the lower half that is consistent with the function of an about box.

Parameters
1. Parent The handle of the windows that calls the dialog box.
2. Instance The instance handle for the application.
3. Icon The handle of the application's icon.
4. appname A zero terminated string that contains the name of the calling application.
5. description A zero terminated string that is used for additional description of the application named in the preceding parameter.
6. copyright A zero terminated string that can contain the copyright information for the application. This parameter can display up to 3 lines of text.

Return Value
The return value is always zero.

Comments
If the Icon handle parameter is zero, a default system icon will be displayed on the system menu. The three parameters that accept zero terminated strings are each displayed in a seperate static text control, the first two can only be displayed as a single line, the 3rd can display up to 3 lines of text to handle typical copyright text.


ArgByNumber

ArgByNumber proc src:DWORD,dst:DWORD,num:DWORD,npos:DWORD

Description
Return the contents of an argument from an argument list by its number.

Parameters
1. src The address of the zero terminated argument list.
2. dst The address of the destination buffer.
3. num The number of the argument to return.
4. npos The next read offset in the source address.

Return Value
The return value is the updated next read offset in the source if it is greater than zero.
The three possible return values are,
> 1 = The next read offset in the source
0 = The end of the argument list has been reached.
-1 = A non matching quotation error has occurred in the source.

Comments
This algorithm supports double quoted text and it is delimited by the space character, a tab or a comma or any combination of these three. It may be used in two seperate modes, single argument mode and streaming mode.

In seperate argument mode you specify the argument you wish to obtain with the "num" parameter and you set the "npos" parameter to zero.
In streaming mode you set a variable to zero and pass it as the 4th parameter "npos" and save the EAX return value back into this variable for the next call to the algorithm. The "num" parameter in streaming mode should be set to one "1".

mov eax, destbuffer      ; load destination buffer
cmp BYTE PTR [eax], 0    ; test its first BYTE
je no_arg                ; branch to no arg handler
print destbuffer,13,10   ; display the argument

Note
To support the notation of an empty pair of double quotes in an argument list, the parser in this algorithm return an empty destination buffer that has an ascii zero as it first character.


ArgCL

ArgCL - ArgCLC

ArgCl proc ArgNum:DWORD, ItemBuffer:DWORD ; GUI version
ArgClC proc ArgNum:DWORD, ItemBuffer:DWORD ; Console version

Description
Both procedures are designed to parse a command line and retreive the specified argument number from the command line if it exists. The GUI version has been superceded by the procedure GetCL which is more flexible across different version of the Windows operating system.

ArgClC is still a valid procedure for console mode applications. Both procedures support quoted text in quotation marks for arguments in the form "long file names" and will retreive arguments from one (1) to the number of arguments on the command line.

Parameters
1. ArgNum Argument number.
2. ItemBuffer Address of buffer to receive the argument if it exists.

Comments
The buffer for the returned argument should be set at 128 bytes in length which is the maximum allowable.

Return Values
0 = no command tail
1 = command tail processed normally
2 = processed but arg does not exist
3 = unmatched quotation marks
4 = empty quotation marks as arg [ "" ]


arr_add
arr_add proc arr:DWORD,cnt:DWORD,plus:DWORD

Description
Add an integer to every member of a DWORD array

Parameters
1. arr Starting address of DWORD array
2. cnt The number of members of the array
3. plus The intege to add to every array member

Return Value
There is no return value.


arr_mul
arr_mul proc arr:DWORD,cnt:DWORD,mult:DWORD

Description
Multiply every member of a DWORD array by an integer.

Parameters
1. arr Starting address of DWORD array
2. cnt The number of members of the array
3. mult The integer to multiply array members by.

Return Value
There is no return value.

Comments
The mult parameter is limited to 16 bit range (65536) because the algorith uses the IMUL mnemonic.


arr_sub

arr_sub proc arr:DWORD,cnt:DWORD,minus:DWORD

Description
Subtract an integer from every member of a DWORD array.

Parameters
1. arr Starting address of DWORD array
2. cnt The number of members of the array
3. minus The integer to subtract from array members.

Return Value
There is no return value.


AsciiDump

AsciiDump proc lpsrc:DWORD,lpbuf:DWORD,lnsrc:DWORD

Description
AsciiDump converts a binary file to assembler DB format.

Parameters
1. lpsrc The address of the byte data to be converted.
2. lpbuf The address of the buffer to receive the results.
3. lnsrc The length of the byte data to be converted.

Return Value
There is no return value.

Comments
This procedure is well suited for programmers who wish to write their own utility to convert binary data to assembler DB format for inclusion into assembler source code.
NOTE : The result is always larger than the source and the buffer must be large enough to receive the data. The buffer should be at least 4 times larger than the source.


atodw

atodw proc uses edi esi String:PTR BYTE

Description
atodw converts a decimal string to dword.
Note that the parameter String is an address of DWORD size.

Parameter
1. String The address of the decimal string to convert

Return Value
The DWORD value is returned in eax.

Example
invoke atodw,ADDR MyDecimalString


atodw_ex

atodw_ex proc lpstring:DWORD

Description
A high speed ascii decimal string to DWORD conversion for applications that require high speed streaming of conversion data.

Parameters
1.lpstring The address of the ascii decimal string.

Return Value
There is no return value.

Comments
This is an extended function aimed at applications where conversion speed is critical to their operation. For non speed critical string to number conversion the normal procedure should be used to save space.


atol

atol proc lpSrc:DWORD

Description
atol converts a zero terminated ascii string signed number into a 32 bit signed integer.

Parameter
1. lpSrc The address of the zero terminate string.

Return Value
The return value is the signed 32 bit integer. See comments

Comments
The algorithm will terminate on the first character less than 30h (The "0" character. The algorithm will strip any leading spaces but if it is used in an environment where leading tabs (ascii 9) are present, the tabs should be removed first.

The algorithm will accept the two sign specifiers "+" and "-" and will treat a numeric string with no sign specifier as a positive integer.

NOTE : The leading sign specifier should not be followed by a space or the procedure will fail.

EXAMPLE
1. - 12345678 will fail
2. -12345678 is correct


bin2byte_ex

bin2byte_ex proc lpword:DWORD

Description
bin2byte_ex is a high speed conversion from a binary notation value to a byte value.

Parameters
1.lpwordThe address of the binary notation string.

Return Value
The return value is the ascii number of the BYTE contained in the binary notation.

Comments
This procedure is suitable for application that must stream binary notation to byte data. It is a large procedure that is aimed at speed rather than minimum size.

NOTE that the input format is not tolerant, it must be 8 characters long and only comprised of the characters 0 and 1 as is normal for binary format data. If the data format you are converting has a trailing "b", it will need to be removed as the algorith only recognises exact 8 character binary notation.


bin2hex

bin2hex proc lpString:DWORD,lnString:DWORD,lpbuffer:DWORD

Description
A high speed binary to formatted HEX algorithm.

Parameters
1.lpString The binary data to be converted to formated HEX.
2.lnString The length of the binary data in BYTES.
3.lpbuffer The address of the destination buffer.

Return Value
The return value is the number of bytes written to the destination buffer.

Comments
The output data is approximately 3 times longer than the source data as it uses 2 characters plus a space for every byte in HEX format. The destination buffer should be at least 3 times the length of the source buffer to hold the result.


BinSearch

BinSearch proc StartPos:DWORD,lpString:DWORD,lnStrng:DWORD,
               lpSubStr:DWORD,lnSubSt:DWORD

Description
BinSearch searchs a source string for a sub string and if found, return the zero based offset of the sub string. This algorithm is ideally suited for binary search where zero terminated string functions are unsuitable.

Parameters
1. StartPos The zero based offset in the source string to start searching from.
2. lpString The address of the string to be searched.
3. lnStrng The length of the string to be searched.
4. lpSubStr The address of the sub string to search for.
5. lnSubSt The length of the sub string.

Return Value
Return value is the zero based offset of the first substring found in the source string or -1 if no substring is found.

Comments
Care should be taken to accurately set the length of both the source string and the sub string, this algorithm searches the full range of ascii characters so it can be used for searching binary files for BYTE sequences. Note that it does not depend on a zero terminator to determine the length of the source or sub strings so if the source or sub string lengths are incorrect, a general protection fault will occur after the end of the buffer has been read.

This algorithm has no error detection to keep its speed in relation to recursive searching so the parameters must be correct to avoid failure.


BitmapFromFile

BitmapFromFile proc pszFileName:DWORD

Description
BitmapFromFile returns a bitmap handle from an image file.
An image may be in either .bmp, .gif, .jpg, or .wmf format

Parameters
1. pszFileName pointer to the pathname of an image file

Return Value
The return value is a handle to a bitmap representation of the file compatible with the screen device context. If the function fails, the return value is NULL. To get extended error information, call GetLastError.

Comments
This function is provided as a convenience to the MASM32 community. It is not composed of highly optimized assembly code, so do not expect blinding speed.

This function uses certain aspects of the Windows API to do the actual conversion from the particular image format. Since the function contains no proprietary code, it may be used without any royalty payments. This may be especially important to those wishing to use .gif files.


BitmapFromMemory

BitmapFromMemory proc pHeap:DWORD, dwSize:DWORD

Description
BitmapFromMemory returns a bitmap handle from a program resource.
An image may be in either .bmp, .gif, .jpg, or .wmf format

Parameters
1. pHeap Address of a memory structure of an image structure.
2. dwSize Size of the memory structure in bytes.

Return Value
The return value is a handle to a bitmap representation of the file compatible with the screen device context. If the function fails, the return value is NULL. To get extended error information, call GetLastError.

Comments
This function is provided as a convenience to the MASM32 community. It is not composed of highly optimized assembly code, so do not expect blinding speed.
This function uses certain aspects of the Windows API to do the actual conversion from the particular image format. Since the function contains no proprietary code, it may be used without any royalty payments. This may be especially important to those wishing to use .gif files.


BitmapFromResource

BitmapFromResource proc hModule:DWORD, lpName:DWORD

Description
BitmapFromResource returns a bitmap handle from a program resource.
An image may be in either .bmp, .gif, .jpg, or .wmf format

Parameters
1. hModule Handle to the module whose executable file contains the resource. A value of NULL specifies the module handle associated with the image file that the operating system used to create the current process.

2. lpName If the high-order word of the lpName parameter is zero, the low-order word specifies the integer identifier of the name or type of the given resource. Otherwise, those parameters are long pointers to null-terminated strings. If the first character of the string is a pound sign (#), the remaining characters represent a decimal number that specifies the integer identifier of the resource's name or type. For example, the string "#258" represents the integer identifier 258.

An application should reduce the amount of memory required for the resources by referring to them by integer identifier instead of by name.

Resource file entries should use the identifier “IMAGE” for all image files to be loaded by this procedure. For backwards capability, bitmap files may have the identifier “BITMAP”

Return Value
The return value is a handle to a bitmap representation of the file compatible with the screen device context. If the function fails, the return value is NULL. To get extended error information, call GetLastError.

Comments
This function is provided as a convenience to the MASM32 community. It is not composed of highly optimized assembly code, so do not expect blinding speed.
This function uses certain aspects of the Windows API to do the actual conversion from the particular image format. Since the function contains no proprietary code, it may be used without any royalty payments. This may be especially important to those wishing to use .gif files.


BmpButton

BmpButton proc hParent:DWORD,topX:DWORD,topY:DWORD,
               rnum1:DWORD,rnum2:DWORD,ID:DWORD

Description
BmpButton is a custom control that uses 2 bitmaps for the UP and DOWN positions.

Parameters
1. hParent The handle of the window that thew control will be displayed on.
2. topX The top "x" co-ordinate for the control.
3. topY The top "y" co-ordinate for the control.
4. rnum1 The resource ID for the UP position bitmap.
5. rnum2 The resource ID for the DOWN position bitmap.
6. ID The identification number to attribute to the control.

Return Value
The return value is the handle of the control.

Comments
This function allows the programmer to exactly control the appearance of the bitmap button. When the button is clicked, it sends a WM_COMMAND message to the parent on release as is normal for buttons.

This control should be processed in the message handling proc like a normal button, trap the WM_COMMAND message in the parent of the control and process the wParam parameter to obtain the control ID.


Boyer Moore Algorithms

BMBinSearch proc startpos:DWORD,
                 lpSource:DWORD,srcLngth:DWORD,
                 lpSubStr:DWORD,subLngth:DWORD

BMHBinsearch proc startpos:DWORD,
                  lpSource:DWORD,srcLngth:DWORD,
                  lpSubStr:DWORD,subLngth:DWORD

SBMBinSearch proc startpos:DWORD,
                  lpSource:DWORD,srcLngth:DWORD,
                  lpSubStr:DWORD,subLngth:DWORD

Description
The three algorithms are variations of a Boyer Moore binary search design that is well suited for very high speed searching of binary or text data for a subpattern.

Parameters
1. startpos Zero based start address to nominate where to start searching.
2. lpSource The address of the data to be searched.
3. srcLngth The length of the search data.
4. lpSubStr The address of the pattern to search for.
5. subLngth The length of the pattern to search for.

Return Value
The functions return either the zero based offset of the pattern being searched for or -1 if the pattern does not occur within the data being searched.

Comments
The three algorithms are variations of a Boyer Moore design. The original design BMBinSearch is the most flexible across different search conditions. The two variations BMHBinsearch and SBMBinSearch are respectively a Horspool variation and a simplified variation which perform well depending on the hardware and the patterns being searched.

The minimum pattern length is 2 bytes but these algorithms are slower on very short paterns than a classic byte scanner. The algorithms have about a 300 character penalty at startup as they must construct a table so for either very short patterns or short data it is more efficient to use a byte scanner. BinSearch

Care should be taken to ensure the first parameter startpos is not past the end of the data being searched.


BrowseForFolder

BrowseForFolder proc hParent:DWORD, lpBuffer:DWORD, lpTitle:DWORD,lpString:DWORD

Description
BrowseForFolder is a system dialog from the shell32 library that is used to search for folders(directories).

Parameters
1. hParent The handle of the application calling the dialog.
2. lpBuffer 260 byte buffer that receives the path data if selection has been made.
3. lpTitle The address of the zero terminated title text for the dialog.
4. lpString The address of the zero terminated string for the secondary title.

Return Value
If a folder is selected, the full path is returned in the buffer supplied in the second parameter.

Comments
The application must include the shell32 and ole32 libraries and include files.


byt2bin_ex

byt2bin_ex proc var:BYTE,buffer:DWORD

Description
A high speed BYTE to binary format converter.

Parameters
1.varThe BYTE value to convert
2.bufferThe address of the buffer to receive the result.

Return Value
There is no return value.

Comments
The result will be 8 characters long plus the terminator so the destination buffer should be 12 bytes for alignment purposes.


byte_count

byte_count proc src:DWORD,cnt:DWORD,array:DWORD

Description
Count every character in a source file

Parameters
1. src Address of memory containing the characters to count
2. cnt Length of the data in BYTES
3. array Address of a 256 member DWORD array

Return Value
The count of every character is in its location in the 256 character array.

Comments
The array must be zero filled. Individual character counts can be retrieved with code such as the following.

mov eax, array             ; array address
xor edx, edx               ; clear EDX to avoid register stall
mov dl, ":"                ; copy required character into DL
mov ecx, [eax+edx*4]       ; get the count from the array for the character


circle

circle proc hndl:DWORD,colr:DWORD,tx:DWORD,ty:DWORD,lx:DWORD,ly:DWORD

Description
This function will display a circle or elipse within the rectangle bounded by the four parameters.

Parameters
1. hndl The window handle of the window where the circle is to be displayed.
2. colr The RGB COLORREF value for the colour of the circle.
3/4 tx, ty The top left co-ordinates for the bounding rectangle.
5/6 lx, ly The bottom right co-ordinates for the bounding rectangle.

Return Value
There is no return value.

Comments
You can make a COLORREF value in eax by using the following macro. Note that the three values are BYTE in size.

RGB MACRO red, green, blue
  xor eax, eax
  mov al, blue   ; blue
  rol eax, 8
  mov al, green  ; green
  rol eax, 8
  mov al, red    ; red
ENDM


ClearScreen

ClearScreen proc

Description
ClearScreen clears the console window and places the text cursor at position 0,0. It takes no parameters and does not return a value.
The following macro makes this procedure easier and faster to use.

cls MACRO
  invoke ClearScreen
ENDM


CloseMMF

CloseMMF proc lpMem:DWORD,hMMF:DWORD

Description
CloseMMF closes a memory mapped file opened by the CreateMMF procedure.

Parameters
1. lpMem The start address of the memory mapped file returned by the CreateMMF procedure.
2. hMMF The handle returned by the CreateMMF procedure.

Return Value
There is no return value.

Comments
When more than one application has opened the same named memory mapped file, the file is not closed until the last application that has opened it closes the file. It is safe to call this procedure even if the memory mapped file is still being used by another application as the operating system will leave it open until the last application using it closes it.


Cmpi

Cmpi proc src1:DWORD,src2:DWORD

Description
A table driven high speed case insensitive text comparison algo.

Parameters
1. src1 The address of the first zero terminated text.
2. src2 The address of the second zero terminated text.

Return Value
If the two text sources match as case insensitive, the return value is ZERO otherwise the return value is non zero.

Comments
This version differs from szCmpi in that it detects the zero terminator without the need for the length to be specified as an additional argument.


cmpmem
cmpmem proc buf1:DWORD,buf2:DWORD,bcnt:DWORD

Description
Compare two memory of the same known length.

Parameters
1.buf1 The first memory location to test
2.buf2 The second memory location to test against the first
3.bcnt The length of the buffers in BYTES.

Return Value
0 = different.
non 0 = byte identical.

Comments
The procedure is useful among other things for testing the contents of two files to see if they are the same.


ColorDialog

ColorDialog proc hWin:DWORD, instance:DWORD, Flags:DWORD

Description
ColorDialog is a system common dialog used for selecting colors.

Parameters
1. hWin The handle of the calling application.
2. instance The instance handle of the calling application.
3. Flags A set of values that can be combined to change the opening characteristics.

Return Value
The RGB value selected or zero.

Comments
The Flags value will accept either 0 for the default Color Dialog or the style CC_FULLOPEN to display the dialog with the custom color option displayed.


Comb Sort

CombSortA proc Arr:DWORD,aSize:DWORD
CombSortD proc Arr:DWORD,aSize:DWORD

Description
The algorithms differ only in that they sort in opposite directions, CombSortA sorts in Ascending order, CombSortD sorts in Descending order.

Parameters
1. Arr The starting address of the array
2. aSize The number of members in the array.

Return Value
There is no value returned from this procedure.

Comments
A comb sort is a design that collapses to a bubble sort when the predetermined GAP closes to zero. It is competitive with most traditional sorting methods and it has the advantage of simplicity and reasonably small code size. The comb sort is an "in place" sort that does not allocate additional memory so it can be used in places where memory usage must be kept under control.


create_array

create_array proc acnt:DWORD,asize:DWORD

Description
Create an array of pointers to a user defined array of user defined length and member count.

Parameters
1. acnt The number of members of the array
2. asize The size of each member in bytes

Return Value
The address of the array of pointers is returned in EAX
The address of the memory for the main array is returned in ECX

Comments
The asize parameter should always be set to a length that is divisible by 4 to maintain the alignment of the following array member otherwise there will be a serious performance penalty due to misaligned reads from memory. When the array is no longer required, both return values should be deallocate using either,

GlobalFree()
  or the MASM32 macro
free


CreateMMF

CreateMMF proc lpName:DWORD,bcnt:DWORD,lphndl:DWORD,lpMemFile:DWORD

Description
CreateMMF creates a memory mapped file from the system paging file that can be shared by other application in seperate processes.

Parameters
1. lpName The zero terminates string that names the file
2. bcnt The size of the required memory mapped file in BYTES.
3. lphndl The address of a DWORD variable to receive the address of the memory mapped file handle.
4. lpMemFile The address of a DWORD variable to receive the start address of the memory mapped file.

Return Values
The lphndl and lpMemFile have the file handle and start address written to them when the procedure returns. There is no return value in EAX.

Comments
A memory mapped file backed by the system paging file is effectively allocated memory but it has the attribute of being sharable between applications that call the same file name. This allows applications to share data by reading and writing to the memory mapped file.

NOTE that a memory mapped file allocate at a specified size cannot be reallocated to a different size. The file must be closed by all applications that access it and then reallocated to a different size. Use CloseMMF to close the memory mapped file.

Example
LOCAL hMMF :DWORD
LOCAL lpMMFile :DWORD

invoke CreateMMF,SADD("Memory_Mapped_File"),
                 1000000,ADDRhMMF,ADDR lpMMFile


decomment

decomment proc src:DWORD

Description
This procedure removes the comment from a single line of source code and trims any trailing spaces or tabs from the source.

Parameters
1. src The address of a zero terminated single line of source code.

Return Value
There are 3 possible return values.
1 = There is more code on the following line that is part of the same statement.
0 = Line of code is complete.
-1 = Quotation error, no closing quotation.

Comments
If the line of source code contains a comment, the result is written back to the same buffer. This algorithm supports both single and double quotations as alternate quotations. The line of code has trailing spaces and tabs removed. The comment character is the normal assembler ";" but the algorithm can be copied and this character can be changed to any other character.


DisplayBmp

DisplayBmp proc hParent:DWORD,bmpID:DWORD,x:DWORD,y:DWORD,ID:DWORD

Description
DisplayBmp encapsulates a static control set with the SS_BITMAP style to display a bitmap in the client area of a window.

Parameters
1. hParent Handle of window that the bitmap will be displayed on.
2. bmpID The resource ID number for the bitmap to be displayed.
3. x The top "x" co-ordinate to position the bitmap
4. y The top "y" co-ordinate to position the bitmap.
5. The ID number for the static control.

Return Value
The return value is the handle of the static control.

Comments
This procedure should be called from the WM_CREATE message in a window or a WM_INITDIALOG in a dialog box. It should NOT be placed in a WM_PAINT message.


DisplayIcon

DisplayIcon proc hParent:DWORD,iconID:DWORD,x:DWORD,y:DWORD,ID:DWORD

Description
DisplayIcon encapsulates a static control set with the SS_ICON style to display an icon in the client area of a window.

Parameters
1. hParent The handle of the window to display the icon on.
2. iconID The resource ID of the icon to display.
3. x The top "x" co-ordinate to position the icon.
4. y The top "y" co-ordinate to position the icon.
5. The ID number for the static control.

Return Value
The return value is the handle of the static control.

Comments
This procedure should be called from the WM_CREATE message in a window or a WM_INITDIALOG in a dialog box. It should NOT be placed in a WM_PAINT message.


dw2ah

dw2ah proc public dwValue:DWORD, lpBuffer:PTR BYTE

Description
dw2ah converts DWORD size data to a hexadecimal ascii string.
Note that the data type PTR BYTE is a DWORD address of BYTE data.

Parameters
1. dwValue is the value to be converted
2. lpBuffer is the address of the receiving buffer

Return Value
There is no return value

Comments
lpBuffer must be at least 10 bytes long


dw2bin_ex

dw2bin_ex proc var:DWORD,buffer:DWORD

Description
A high speed DWORD to binary conversion.

Parameters
1.var The DWORD to be converted.
2.buffer The destination address.

Return Value
There is no return value.

Comments
The resultinfg output is 32 characters in length so the destination buffer must be 32 plus a terminator. A buffer of 36 bytes is recommended for alignment reasons.


dw2hex

dw2hex proc source:DWORD, lpBuffer:DWORD

Description
dw2hex converts a DWORD value to an ascii hex string.

Parameters
1. source The DWORD value to convert
2. lpBuffer The address of the buffer to receive the ascii hex string

Return Value
There is no return value.

Comments
The buffer for the result needs to be 8 bytes long plus one byte for the terminator so for alignment, make the buffer 12 bytes long.


dw2hex_ex

dw2hex_ex proc src:DWORD,buf:DWORD

Description
A high speed DWORD to HEX conversion.

Parameters
1.srcThe source DWORD to convert.
2.bufThe address of the destination buffer for the result.

Return Value
There is no return value.

Comments
This algorithm is designed for applications that must stream such conversions at high speed. Non critical applications should use the normal procedure to save space.


dwtoa

dwtoa proc public uses esi edi dwValue:DWORD, lpBuffer:DWORD

Description
dwtoa convert a DWORD value to an ascii string.

Parameters
1. dwValue The DWORD value to convert.
2. lpBuffer The address of the buffer to put the converted DWORD into.

Return Value
There is no return value.

Comments
The buffer for the converted value should be large enough to hold the string including the terminating zero.


exist

exist proc lpszFileName:DWORD

Description
This function tests if a file exists at the path and file name in the zero terminated string.

Parameter
1. lpszFileName The zero terminated string that has the path & name of the file to test.

Return Value
If the return value in eax is zero, the file does not exist, if it is 1, then it exists.


filesize

filesize proc lpszFileName:DWORD

Description
This function returns the length of a file if it exists.

Parameter
1. lpszFileName The zero terminated string that has the path & name of the file.

Return Value
If the return value is minus one (-1) then the file does not exist, otherwise eax returns the size of the file in bytes.

Comments
This function will return the size of a file without opening it so it can be used to check the length of a running EXE file.


FloatToStr

FloatToStr  PROCstdcall public USES esi edi, fpin: QWORD, szDbl: PTR CHAR
FloatToStr2 PROCstdcall public USES esi edi, fpin: QWORD, szDbl: PTR CHAR

Note that szDbl is a DWORD size address of the buffer to receive the string data.

Description
FloatToStr converts a QWORD size floating point value to a string. FloatToStr2 differs only in that it outputs a larger number in normal notation before it starts to use engineering notation.

Parameters
1. fpin The QWORD value to convert.
2. szDbl The address of the buffer to place the result in.

Return Value
There is no return value.

Comments
The buffer for the string should be at least 19 bytes long as the procedure always write an 18 byte long string in szDbl. For alignment considerations, a 20 byte long buffer is recommended.


FontDialog

FontDialog proc hWin:DWORD, lf:DWORD, fStyle:DWORD

Description
FontDialog is a system common dialog for retreiving the name of a selected font.

Parameters
1. hWin The handle of the calling application's window.
2. lf The address of a LOGFONT structure.
3. fStyle Style(s) for the CHOOSEFONT structure.

Return Value
If eax returns zero, cancel was pressed. If selection is made, return in eax is non zero and LOGFONT structure is filled with font information.

Comments
The fStyle parameter is a set of styles that may be OR'd together to acheive the required effect. The reference for the styles are in the win32.hlp file for the CHOOSEFONT structure.


Frame3D

Frame3D proc hDC:DWORD,btn_hi:DWORD,btn_lo:DWORD,
             tx:DWORD, ty:DWORD, lx:DWORD, ly:DWORD,bdrWid:DWORD

Description
Frame3D will draw a 3D frame in the client area of a window at the co-ordinates provided.

Parameters
1. hDC You must provide a device context for this function.
2. btn_hi The nominal highlight colour.
3. btn_lo The nominal lowlight colour.
4 to 7. tx, ty, lx, ly The four co-ordinates for the rectangular area. The units are in pixels.
8. bdrWid The border width specified in pixels.

Return Value
There is no return value.

Comments
The rectangle drawn increases outwards as the border width increases.


FrameCtrl

FrameCtrl proc hCtrl:DWORD, step:DWORD, wdth:DWORD, direction:DWORD

Description
This procedure draws a frame around a control onto the client area of the window. It has the option of how many pixels to step outwards from the control and can draw either a raised or sunken frame.

Parameters
1. hCtrl The handle of the control to draw the frame around.
2. step The number of pixels to step outwards from the control.
3. wdth The width of the border in pixels.
4. direction Frame type, 0 for sunken frame, 1 for raised frame.

Comments
This procedure uses the Frame3D procedure to draw the frame onto the client area of the window. It is important to supply a control handle and not a control ID number. If you are using a control in a dialog box, you need to convert the ID number to a handle.


FrameGrp

FrameGrp proc hCtrl1:DWORD, hCtrl2:DWORD, step:DWORD, wdth:DWORD, direction:DWORD

Description
This proc draws a frame bounded by the top left co-ordinates of the first control handle and the bottom right co-ordinates of the second control handle. It is used to draw frames around groups of controls.

Parameters
1. hCtrl1 The control that has the top left corner position.
2. hCtrl2 The control that has the lower right corner position.
3. step The distance in pixels outwards from the controls to draw the frame.
4. wdth The width of the frame in pixels.
5. direction The direction of the frame. 0 = sunken frame, 1 = raised frame.

Comments
This procedure is designed to work on a group of controls, typically a group of same size buttons where the whole group is framed. It is important that both of the control handles are valid window handles and not ID numbers. If the group of controls to be framed are dialog box controls, the ID number of both controls must be converted to window handles.


FrameWindow

FrameWindow proc hndle:DWORD, step:DWORD, wid:DWORD, direction:DWORD

Description
This procedure is used for framing the client area of a window. It uses the co-ordinates of the window to determine the correct dimensions for the frame position.

Parameters
1. hndle The handle of the window.
2. step The number of pixels inside the window's client area to start the frame.
3. wid The width of the frame in pixels.
4. direction The direction of the frame, 0 = sunken, 1 = raised.

Comments
This procedure uses the Frame3D procedure to draw the frame onto the client area of the window. The handle must be a valid window handle. If you need to frame a dialog box, you must convert the dialog box ID number to a window handle first.


Free

Free proc public pv:DWORD

Description
Free frees a block of memory that was allocated by Malloc.

Parameter
1. pv Address returned by Malloc when memory was allocated.

Return Value
There is no return value.

Comments
Free frees a block of memory previously allocated through a call to Malloc. The number of bytes freed equals the number of bytes that were allocated. After the call, the memory block pointed to by pv is invalid and can no longer be used.

Note The pv parameter can be NULL. If so, this method has no effect.


get_ml

get_ml proc src:DWORD,dst:DWORD,rpos:DWORD

Description
get_ml is an algorithm to read the next statement from source code. The statement may be multiline with comments at the end of each line.

Parameters
1. src The address or the zero terminated source code.
2. dst The address of the destination buffer.
3. rpos The next read offset in the source code.

Return Value
There are 3 possible return values.
>0 = next read offset in source
0 = end of source data
-1 = quotation error, non matching quotes.

Comments
The algorithm supports both single and double quotations as alternate quotations and determines the quotation type by the first quote in the argument. It recognised two types of split line indicators, a trailing comma or a trailing "\" character for split lines on constants and similar. This algorithm uses the normal assembler comment character ";" but the complete algorithm can be copied and this can be changed to any other single character.

The output is the complete next statement in the source code with comments and CRLF pairs removed in the destination buffer. Note that no special formatting has been applied to the data as a normal tokeniser can normally handle unused spaces.

Example
This simple example scans through a complete source and displays each complete code statement at the console.

  mov rpos, 0
stlp:
  mov rpos, rv(get_ml,hMem,hBuf,rpos)
  print hBuf,13,10
  cmp rpos, 0
  jnz stlp


GetAppPath

GetAppPath proc lpPathBuffer:DWORD

Description
GetAppPath returns the address of the running application's path as a zero terminated string with the filename removed. The last character in the string is a trailing backslash "\" to facilitate parsing different filenames to the path.

Parameter
lpPathBuffer The address of the buffer that will receive the application path.

Return Value
There is no return value.

Comments
The buffer size should be 128 bytes long.


GetCL

GetCL proc ArgNum:DWORD, ItemBuffer:DWORD

Description
GetCl will retreive the argument specified in the procedure call and return the argument in the buffer specified. It differs slightly in its implementation in that it treats the path and name of the application making the call as arg 0.

Arguments are specified from arg 1 up to the number of command line arguments available. The procedure supports the retreival of arguments that are enclosed in quotation marks and will return the argument with the quotation marks removed.

Parameters
1. ArgNum Argument number.
2. ItemBuffer Address of buffer to receive the argument if it exists.

Return values
1 = successful operation
2 = no argument exists at specified arg number
3 = non matching quotation marks
4 = empty quotation marks

Comments
The buffer for the returned argument should be set at 128 bytes in length which is the maximum allowable.

Example
invoke GetCl, 1, ADDR ItemBuffer
If arg 1 exists, the procedure will place the argument in the buffer ItemBuffer.


getcl_ex

getcl_ex proc num:DWORD,pbuf:DWORD

Description
Extended version of GetCL.

Parameters
1. num The argument number to return from a command line.
2. pbuf The buffer to receive the selected argument.

Return Value
There are three (3) possible return values.
1 = successful operation
2 = no argument exists at specified arg number
3 = non matching quotation marks

Comments
This algorithm uses the ArgByNumber procedure to obtain the selected argument from a command line. It differs from the original version in that it will read a command line of any length and the arguments can be delimited by spaces, tabs, commas or any combination of the three.

It is also faster but as the ArgByNumber procedure is table driven, it is also larger.


GetClipboardText

Description
Read text from the clipboard if it is available and copy that text to a block of memory allocated with GlobalAlloc().

Parameters
The function takes no arguments. Use it as follows,
invoke GetClipboardText

Return Value
The return value is either zero (0) if no text is available on the clipboard or the return value is a GlobalAlloc() handle to memory that contains the clipboard text. Treat this handle as a direct memory pointer.

Comments
If the return value was NOT zero and a memory handle is returned, when the text is no longer required deallocate the memory with GlobalFree() or the macro "free". This does not neeed to be done if there was no text on the clipboard.


GetFile

GetFile proc Parent :DWORD,Instance :DWORD,Icon:DWORD,
             caption:DWORD,directory:DWORD,
             pattern:DWORD,buffer :DWORD

Description
The GetFile prebuilt dialog is designed to quickly get a file name from a predefined directory. It does not display directories or drives and uses a sorted list box to display the files for the chosen pattern.

Parameters
1. Parent The handle of the windows that calls the dialog box.
2. Instance The instance handle for the application.
3. Icon The handle of the application's icon.
4. caption A zero terminated string that is displayed on the title bar of the dialog.
5. directory A zero terminated string for the directory that the dialog is to display files in
6. pattern. A zero terminated string that has the file pattern required
7. buffer The address of a memory buffer that is large enough to hold the maximum length filename that can be displayed, this should be 260 bytes.

Return Value
The return value is always zero in EAX.

Comments
The buffer should be tested to see if the first BYTE is zero which indicates that the user cancelled the operation. If it is not zero, it will be the zero terminated string that contains the name of the selected file.


GetIP

GetIP proc Instance :DWORD,Parent:DWORD, Icon:DWORD,
           lpCaption:DWORD,lpText:DWORD,defIP:DWORD

Description
Dialog displays an IP control that can be optionally set with a default IP. It can be used to obtain an IP from a user or alternatively display a default IP with the user having the option to change it.

Parameters
1. Parent The handle of the windows that calls the dialog box.
2. Instance The instance handle for the application.
3. Icon The handle of the application's icon.
4. lpCaption A zero terminated string that has the caption required for the dialog box.
5. lpText A zero terminated string if text is required above the IP control for extra explanation to the user.
6. defIP The default IP address as a DWORD size variable.

Return Value
If the user cancels the operation, the return value in EAX is -1, else it is the IP as a single DWORD value. To convert the IP value to a string for display, use the IPtoString procedure. To make a single DWORD value IP address, use the macro MakeIP displayed below. It is contained in the include file MASM32.INC.

MakeIP MACRO val1,val2,val3,val4
  mov ah, val1
  mov al, val2
  rol eax, 16
  mov ah, val3
  mov al, val4
  EXITM <eax>
ENDM


GetPathOnly

GetPathOnly proc src:DWORD, dst:DWORD

Description
GetPathOnly reads the path of a complete file path and returns the path portion in the destination buffer.

Parameters
1. src Address of source zero terminated path.
2. dst Address of buffer to receive the path portion of a complete path.

Return Value
This procedure has no return value.

Comments
The destination buffer must be large enough to receive the path from the complete path.


GetPercent

GetPercent proc source:DWORD, percent:DWORD

Description
GetPercent calculates the percentage of the source specified in the second parameter.

Parameters
1. source Integer to obtain a percentage value from.
2. percent an integer between 1 and 100 to set the percentage required.

Return Value
The return value is the set percentage of the source in eax.

Comments
The return value is rounded down to the next integer value. This procedure was primarily designed to handle screen size percentages where integer return values are appropriate.


GetTextInput

GetTextInput proc hParent :DWORD,Instance :DWORD,
                  Icon :DWORD,caption :DWORD,
                  subcaption:DWORD,lpbuffer :DWORD

Description
The GetTextInput dialog is used to obtain text from the user. It has the option to display an additional text field above the edit control where the user enters the text.

Parameters
1. Parent The handle of the windows that calls the dialog box.
2. Instance The instance handle for the application.
3. Icon The handle of the application's icon.
4. caption A zero terminated string that contains the text to display on the title bar of the dialog.
5. subcaption A zero terminated string that contains the text to display in the addition field above the edit conrol.
6. lpbuffer The address of the buffer that will receive the text entered by the user. This buffer should be at least 128 bytes in length.

Return Value
The return value in EAX is always zero.

Comments
To test if the user has entered text, the first byte of the buffer should be tested for zero. If the value is not zero, the buffer contains the text typed by the user.


hex2bin

hex2bin proc src:DWORD,dst:DWORD

Description
A high speed algorithm that will convert formated hex from the same format as bin2hex procedure output back to binary.

Parameters
1.src The address of the formatted HEX data.
2.dst The address of the destination buffer.

Return Value
0 = no error
1 = invalid hex format, characters must be in pairs.
2 = illegal character in source.

Comments
This algorithm allow the user to write formatted HEX complete with side comments using ";" and convert the results to binary. The error conditions are to ensure that the HEX format saved as binary is valid. Notation for HEX must be in character pairs and characters that are not used in HEX notation will produce an error.


HexDump

HexDump proc lpString:DWORD,lnString:DWORD,lpbuffer:DWORD

Description
HexDump takes a byte sequence or string, text or binary and converts it to an ascii hex dump.

Parameters
1. lpString The address of the byte sequence or string to convert.
2. lnString The length of the byte sequence or string
3. lpbuffer The address of a buffer large enough to receive the results.

Return Value
There is no return value

Comments
The result is always larger than the source string or byte data so the buffer must be larger to receive it. In most circumstances, making the buffer 4 times the size of the source data is safe.


hexflip32

hexflip32 proc src:DWORD

Description
A special purpose algorithm for converting normal hex to memory order hex.

Parameters
1.src The address of the hex string to convert to memory order.

Return Value
The converted data is written back to the source buffer.

Comments
The algorithm accepts assembler format hex notation with the trailing "h" and optionally a leading "0" if required. Total string length must not exceed 10 bytes including the "h" and "0".
Output is a memory order hex string that is always 8 bytes long. If the input string is less than 8 bytes in length the output string is padded with trailing "0" s to make up the length.
The output is always written to the source string buffer and the buffer must be at least 9 bytes long. A buffer of 12 bytes satisfies alignment criterion.
01199AAFFh becomes "FFAA9911"


htodw

htodw proc uses ebx ecx edi edx esi String:DWORD

Description
htodw receives as its parameter, the address of a zero terminated string containing hex characters and returns the value as a DWORD in eax.

Parameter
1. String The address of the zero terminated string to be converted.

Return Value
The DWORD value is returned in eax.

Comments
It is the users responsibility to ensure that there are no non-hexadecimal characters in the string of numbers.


iFree

Free

Free proc public pv:DWORD

Description
Free frees a block of memory that was allocated by Malloc.

Parameter
1. pv Address returned by Malloc when memory was allocated.

Return Value
There is no return value.

Comments
Free frees a block of memory previously allocated through a call to Malloc. The number of bytes freed equals the number of bytes that were allocated. After the call, the memory block pointed to by pv is invalid and can no longer be used.

Note The pv parameter can be NULL. If so, this method has no effect.


iMalloc

Malloc

Malloc proc public cb:DWORD

Description
The Malloc method allocates a memory block in essentially the same way that the C Library malloc function does.

Parameter
1. cb The number of bytes to allocate.

Return Value
If cb is zero, Malloc allocates a zero-length item and returns a valid pointer to that item. If there is insufficient memory available, Malloc returns NULL.

Comments
The initial contents of the returned memory block are undefined and there is no guarantee that the block has been initialized, so you should initialize it in your code. The allocated block may be larger than cb bytes because of the space required for alignment and for maintenance information.

Note Applications should always check the return value from this method, even when requesting small amounts of memory, because there is no guarantee the memory will be allocated.


MASM32 Library Reference
Copyright (c) The MASM32 project 1998-2007

MASM32.LIB is a collection of procedures to supply additional functionality to the MASM32 project. Each procedure has been written as a seperate module to prevent any granularity problems

The full source code for the MASM32 library is in the M32LIB directory in MASM32.

To use these procedures your code needs to include both the following two (2) lines in your main assembler file.

     include \masm32\include\masm32.inc
     includelib \masm32\lib\masm32.lib
Categories of library procedures.

Arithmetic
Command Line
Conversions
Extended Functions
Custom Control
Encryption Components
Floating Point Conversions
File Functions
Console Mode Functions
Graphics Primitives
Image Functions
Memory Functions
String Sorting
Recommendations with string sorts
C Style Character Testing
Parsing Functions
 Search Functions
         Pre-Built Dialogs
Sorting Functions
Clipboard Functions
Zero Terminated String Functions
Obsolete String Functions
System Dialogs
Window Framing Functions
Path Functions
Rich Edit Functions
Misc
Array Functions
Unicode String Functions
Unicode Common Dialogs
Hex to Binary Conversions
In Memory Text Read and Write
Tokenisers


InString

InString proc StartPos:DWORD, lpszString:DWORD, lpszSubStr:DWORD

Description
InString searches for a substring in a larger string and if it is found, it returns its starting position in eax. It uses a one (1) based character index (1st character is 1, 2nd is 2 etc...) for both the "StartPos" parameter and the returned character position.

Parameters
1. StartPos Starting position to search for the substring.
2. lpszString Address of string to be searched.
3. lpszSubStr Address of substring to search for within the main string.

Return Values.
If the function succeeds, it returns the 1 based index of the start of the substring or 0 if no match is found.

Error Values
If the function fails, the following error values apply.
-1 = substring same length or longer than main string
-2 = "StartPos" parameter out of range (less than 1 or greater than main string length)

Example
invoke InString,1,ADDR szMainString,ADDR szSubString
mov txtPos, eax


IntDiv

IntDiv proc source:DWORD,divider:DWORD

Description
IntDiv divides the source by the divider.

Parameters
1. source DWORD size source integer
2. divider DWORD size divider

Return Value
The return value is the result of the integer division returned in eax.

Comments
The results are subject to integer resolution which will round down the result. This effect will be particularly noticable on small numbers.


IntMul

IntMul proc source:DWORD,multiplier:DWORD

Description
IntMul performs integer multiply on a DWORD size source by the multiplier.

Parameters
1. source DWORD size integer
2. multiplier DWORD size multiplier

Return Value
The return value is the result returned in eax.

Comments
The results are bound by DWORD size and no attempt is made to handle overflow so the size limit is about 4 gigabytes.


IntSqrt

IntSqrt proc source:DWORD

Description
IntSqrt produces the square root of the source integer and returns it in EAX.

Parameters
1. source is the 32 bit integer to get the square root from.

Return value
The return value in EAX is the square root of the source.

Comments
This is an integer function that rounds down to the next integer. Note that this rounding error on small numbers is substantial.


IPtoString

IPtoString proc IP:DWORD,lpBuffer:DWORD

Description
IPtoString is a procedure to convert a single DWORD IP value to a zero terminated string for display.

Parameters
1. IP The single DWORD value that contains the IP address.
2. lpBuffer A buffer that is large enough to hold the maximum length result of an IP

Return Value
The result is written to the buffer supplied in the second parameter. There is no return value in EAX.

Comments
The longest string that this procedure can return is 21 bytes plus the terminating zero. It is recommended that the buffer allocated for this result be 24 bytes for alignment purposes.


isalpha

isalpha proc char:BYTE

Description
A C style procedure to test if a character is alphabetic.

Parameters
1.char The character to test

Return Value
0 = character is non alphabetic
1 = character is upper case
2 = character is lower case

Comments
While this procedure is easy to use, if speed is critical, there is a macro chtype$() that is substantially faster in the MACROS.ASM file.


isalphanum

isalphanum proc char:BYTE

Description
A C style procedure to test if a character is alpha - numeric.

Parameters
1.charThe character to test.

Return Value
0 = Not alpha - numeric.
1 = Numeric character.
2 = Upper case character.
3 = Lower case character

Comments
While this procedure is easy to use, if speed is critical, there is a macro chtype$() that is substantially faster in the MACROS.ASM file.


islower

islower proc char:BYTE

Description
A C style procedure to test if a character is lower case.

Parameters
1.charThe character to test.

Return Value
0 = not lower case.
1 = lower case.

Comments
While this procedure is easy to use, if speed is critical, there is a macro chtype$() that is substantially faster in the MACROS.ASM file.


isnumber

isnumber proc char:BYTE

Description
A C style procedure to test if a character is a decimal number.

Parameters
1.char The character to test.

Return Value
0 = non numeric character.
1 = numeric character.

Comments
While this procedure is easy to use, if speed is critical, there is a macro chtype$() that is substantially faster in the MACROS.ASM file.


isupper

isupper proc char:BYTE

Description
A C style procedure to test if a character is upper case.

Parameters
1.charThe character to test.

Return Value
0 = not upper case
1 = upper case

Comments
While this procedure is easy to use, if speed is critical, there is a macro chtype$() that is substantially faster in the MACROS.ASM file.


lfcnt

lfcnt proc txt:DWORD

Description
Return the number of line feeds in a zero terminated text.

Parameters
1. txt The address of the text to count line feeds in

Return Value
The return value is the number of line feeds in the source.

Comments
The primary use for this procedure is to count the number of lines in a zero terminated text so it can be used as a counter for processing lines of text.


line

line proc hndl:DWORD,colr:DWORD,x1:DWORD,y1:DWORD,x2:DWORD,y2:DWORD

Description
line will display a line between the first X,Y co-ordinate and the second X,Y co-ordinate.

Parameters
1. hndl The handle of the window where the line will be displayed.
2. colr The RGB COLORREF value for the colour of the line.
3/4 x1, y1 The X, Y co-ordinates of the start of the line.
5/6 x2, y2 The X, Y co-ordinates of the end of the line.

Return Value
There is no return value.

Comments
You can make a COLORREF value in eax by using the following macro. Note that the three values are BYTE in size.

RGB MACRO red, green, blue
  xor eax, eax
  mov al, blue ; blue
  rol eax, 8
  mov al, green ; green
  rol eax, 8
  mov al, red ; red
ENDM


load_drives

load_drives proc list:DWORD

Description
Procedure to load the fixed drives and volume labels into a list box.

Parameters
1. list Handle to a list control.

Return Value
There is no return value.

Comments
The procedure can be modified to accept drives other than fixed drives and the string data can be changed in the list box display. If you need to use this procedure in a different form, copy it to your application using a different name to avoid conflicts with the MASM32 library and modify it to suit your requirements.


LoadList

LoadList proc hWin:DWORD,pattern:DWORD

Description
LoadList load the file names in the current directory into a list box. Long file names are supported.

Parameters
1. hWin The handle of the list box to receive the file names.
2. pattern The address of a zero terminated string that contains the required file pattern..

Return Value
There is no return value.

Comments
Set the current directory using the SetCurrentDirectory() API function call.


locate

locate proc x:DWORD,y:DWORD

Description
The locate function positions the text cursor in the console at whatever position is set in the two parameters.

Parameters
1. x The column number.
2. y The row number.

Return Value
There is no return value.

Comments
The locate function uses a zero based row & column numbering, top left corner is position 0,0.


ltoa

ltoa proc lValue:DWORD, lpBuffer:DWORD

Description
ltoa converts a 32 bit signed integer (LONG) and write the results to a buffer as a zero terminated string.

Parameters
1. lValue The 32 bit signed integer to convert.
2. lpBuffer A buffer of sufficient length to receive the zero terminated string.

Return Value
The number of characters written to the buffer or zero.

Comments
This procedure is a wrapper around the "wsprintfA" Windows API function. The buffer should be long enough to receive the maximum length result. 16 bytes is the recommended buffer size for size and alignment purposes.

Example
1. In the .DATA? section.
buffer db 16 dup (?)
2. As a LOCAL value in a procedure.
LOCAL buffer[16]:BYTE


ltok

ltok proc pTxt:DWORD,pArray:DWORD

Description
Tokenise lines of text "in place" and return an array of pointers to each token.

Parameters
1. pTxt The address of the source text to tokenise.
2. pArray The address of a DWORD variable that will be used for the handle of the array of pointers. Please refer to the comments section for further details.

Return Value
The return value in EAX is the number of tokens in the array of pointers.

Comments
When the address of the variable for the pointer array is passed to the procedure, the procedure in turn writes the address of the allocated memory back to that address so that within the scope of the procedure that allocated the variable and calls the tokeniser, the variable is then the direct pointer to the array of pointers. When the pointer array is no longer needed the variable should be deallocated using GlobalFree() within the same scope as the variable was allocated. The MASM32 macro "free" works correctly for this task.

Example
LOCAL MyVar :DWORD
Pass ADDR MyVar to the tokeniser.
Use MyVar as the address of the array of pointers after the tokeniser has returned.
free MyVar


MemCopy

MemCopy proc public uses esi edi Source:PTR BYTE,Dest:PTR BYTE,ln:DWORD

Note here that the source and destination parameters are DWORD size addresses of the respective source and destination buffers.

Parameters
1. Source Source buffer address.
2. Dest Destination buffer address.
3. ln The number of bytes to copy.

Return Value
There is no return value.

Comments
The destination buffer must be at least the same size as the source buffer otherwise the procedure will write past the end of the destination buffer and cause a write page fault.

Example
invoke MemCopy,ADDR MySource,ADDR MyDest,ln
MemCopy copies the byte count of memory from a source buffer to a destination buffer.


memfill

memfill proc lpmem:DWORD,ln:DWORD,fill:DWORD

Description
memfill is a fast memory filling procedure that works in DWORD unit sizes. It is usually good practice to allocate memory in intervals of four for alignment purposes and this procedure is designed to work with memory allocated this way.

Parameters
1. lpmem The address of the memory block to fill.
2. ln The buffer length to fill.
3. fill The fill character(s).

Return Value
There is no return value.

Comments
In most instances the fill character will be ascii zero but the DWORD value can be arranged in any manner convenient, it also can be loaded as a string which will be repeated at 4 byte intervals.
NOTE that the characters in the string will be reversed so that if you place "1234" in the DWORD variable, it will be written to the memory filled as "43214321" for the length of the filled memory. Also note that the procedure will round down the fill to the next interval of 4 if the buffer does not divide equally by four.


NameFromPath

NameFromPath proc lpPath:DWORD,lpBuffer:DWORD

Description
NameFromPath reads the filename from a complete path and returns it in the buffer specified in the parameter list.

Parameters
1. lpPath is the address of the full path that has the file name.
2. lpBuffer is the address of the buffer to receive the filename.

Return Value
The file name is returned in the buffer supplied in the second parameter.

Comments
The buffer to receive the filename must be large enough to acept the filename. For safety reasons if dealing with both long path and file name, the buffer can be made the same length as the source buffer.


Notes On Encryption

The algorithms in the library are components for constructing encryption systems. They use fundamentally simple low level encryption techniques in XOR, ROL and ROR. The strength of this system is not in the encryption method but in the capacity to use very large keys up to source length keys or longer.

Large keys of source length or longer present considerable problems for cracking encrypted data as it defeats many of the known techniques for of code breaking. There are no sequential repeats in the key, working on a small section of the encrypted data has no advantages and a dictionary attack fails when the key can be any type of data including binary files.

On modern computers, large files like bitmaps are very common so if you work for the KGB, having a badly scanned image of Richard Nixon would work as a key where if you worked for the CIA, a badly scanned image of Leonard Breznev would work as well.

Properly an encryption standard random pad is what should be used and each time the pad should be unique. reuse of the same pad progressively degrades the standard of encryption.

The methods in the library are secure in as much as they are published and therefore public encryption methods.
While the methods are primarily designed for block data encryption being read from and written to disk, there is no reason why they cannot be used for computer security related software and program protection.

XorData is encrypted on the first pass and decrypted on the next using the same key and source data. RolData and RorData are used in pairs where data encrypted with one is decrypted with the other using the same key.

The algorithms work by looping through the key until it finds the end then it repeats the loop so it will handle key data that is shorter than the source data but it is advantageous to use a key the size of the source or larger as there are no repeats in the sequence that can be used to crack the encryption.


nrandom

nrandom proc base:DWORD

Description
A Park Miller random algorithm written by Jaymeson Trudgen (NaN) and optimised by Rickey Bowers Jr. (bitRAKE).

Parameter
1.base Zero based range for random output.

Return Value
Random number within range set in "base" in EAX.

Comments
The seed for the random algorithm is set as a variable of GLOBAL scope in a seperate procedure atached to the library module. The variable is nrandom_seed and this variable should be set with a DWORD size number prior to the use of this algorithm.


OpenFileDialog

OpenFileDialog proc hParent:DWORD,Instance:DWORD,lpTitle:DWORD,lpFilter:DWORD

Description
OpenFileDialog displays a common dialog to obtain the name of a file.

Parameters
1. hParent The handle of the parent window.
2. Instance The application or DLL instance handle.
3. lpTitle The address of a zero terminated string with the dialog title.
4. lpFilter The file pattern(s) to display in the dialog.

Return Value
The return value in EAX is the offset of a dedicated 260 byte buffer for this procedure. If the user selects a file name it will be written to the buffer, if the user cancels the dialog, the first byte in the buffer is set to ascii zero.

Comments
If the pattern is too long to place in the macro, it can be placed in a seperate variable and used in the macro.You should test for the user cancelling the operation by testing the 1st byte in the buffer that is returned in EAX with code similar to the following.

  mov patn, CTXT("all files",0,"*.*",0,"txt files",0,"*.txt;*.ini",0)
  mov fname, OpenFileDlg(hWin,hInstance,SADD("Open File ..."),patn)
  cmp BYTE PTR [eax], 0
  jne @F
  ; code to respond to cancelling the dialog here
@@:


PageSetupDialog

PageSetupDialog proc hWin:DWORD, lppsd :DWORD, style:DWORD,
                     lMargin:DWORD, tMargin:DWORD,
                     rMargin:DWORD, bMargin:DWORD

Description
PageSetupDialog is a system common dialog for setting up parameters for a page to be printed.

Parameters
1. hWin Parent window handle.
2. lppsd Address of PAGESETUPDLG structure for return parameters
3. style Default is 0, else styles from PAGESETUPDLG reference.
4. lMargin 0 defaults to 500, inch = 1000
4. tMargin 0 defaults to 500, inch = 1000
4. rMargin 0 defaults to 500, inch = 1000
4. bMargin 0 defaults to 500, inch = 1000

Return Value
If OK is clicked, the return value is non-zero, if Cancel is clicked, zero is returned.

Comments
If OK is clicked, the PAGESETUPDLG structure is filled with the selection from the dialog.


parse_line

parse_line proc src:DWORD,array:DWORD

Description
Parse words in a line of text into an array of zero terminated strings.

Parameters
1.src The address of the zero terminated line of text.
2.array The array to write the words to.

Return Value
The return value is the number of words written to the array.
The words in the line of text are individually loaded into consecutive array locations.

Comments
The array address passed to the procedure must be an array of pointers to preallocated memory. The "create_array" procedure in the MASM32 library is ideally suited to this task as it allocates the memory and sets the array of pointers to the members of the array.

When you allocate the array of zero terminated strings, you must ensure that the individual buffer size is large enough and there are enough members to handle the maximum number of words on the line of text.

Words are determined by an allowable character table. The procedure was originally designed to parse lines of assembler code so it supports the following characters.

upper case ABCDEFGHIJKLMNOPQRSTUVWXYZ
lower case abcdefghijklmnopqrstuvwxyz
numbers 0123456789
quotation marks " "
square brackets [ ]
address calculation + - *
label identification :

The algorithm is flexible enough to do most normal line parsing requirements.


partial

partial proc startat:DWORD,psrc:DWORD,ppatn:DWORD

Description
Partial string matching algorithm with fixed "*" wildcard support.

Parameters
1. startat : zero based offset from start address.
2. psrc : address of zero terminated source to search.
3. ppatn : address of zero terminated pattern to find.

Return Value
-1 = NO match
0 and greater = zero based offset of match

Comments
Algorithm is a traditional linear scanner with a specialised matching loop to handle included wildcard characters.
Zero terminated string format for the pattern to find occurs in the following format.

For a range of similar words,
test
pest
best
text
The string "*e*t" will match all of them.

NOTE that the algorithm is not designed to handle variable length wildcard ranges, it is specifically designed for fixed character lengths.


PrintDialog

PrintDialog proc hWin:DWORD,lppd:DWORD,flags:DWORD

Description
PrintDialog is a system common dialog that is used to set printing options.

Parameters
1. hWin The handle of the calling application.
2. lppd The address of a PRINTDLG structure.
3. Flags Additional styles from the PRINTDLG reference material.

Return Value
If OK is clicked, the return value is non-zero, if Cancel is clicked, zero is returned.

Comments
The selection parameters are contained in the PRINTDLG structure if cancel was not pressed.


Quick Sort

nrQsortA proc Arr:DWORD,count:DWORD
nrQsortD proc Arr:DWORD,count:DWORD

Description
The algorithms differ only in that they sort in opposite directions, nrQsortA sorts in Ascending order, nrQsortD sorts in Descending order.

Parameters
1. Arr The starting address of the array
2. count The number of members in the array.

Return Value
There is no value returned from this procedure.

Comments
This algorithm type is generally faster than any of the traditional sorting algorithms but in some circumstances, data ordered in unusual ways may effect the speed of the sort. In most instances on random data, the algorithm type is very fast.

NOTE : The oleaut32 library and include file are needed because of the OLE string memory used by the procedure.


read_disk_file

read_disk_file proc lpfname:DWORD,lpMem:DWORD,lpLen:DWORD

Description
read_disk_file reads a disk file into memory and returns the address and length in two DWORD variables.

Parameters
1. lpfname The zero terminated file name.
2. lpMem The address of the DWORD variable that receives the starting address of the buffer.
3. lpLen The address of the DWORD variable that receives the number of bytes written to the memory buffer.

Return Value
The return value is non zero if the file is opened and zero if the procedure fails.

Comments
The lpMem value should be deallocated using GlobalFree() once the memory for the file content is no longer required.


Read_File_In

Read_File_In proc hEdit:DWORD,lpszFileName:DWORD

Description
Read_File_In reads the file specified in the second parameter and loads it into the edit control specified in the first parameter.

Parameters
1. hEdit is the handle of the rich edit control to be loaded.
2. lpszFileName is the address of a zero terminated filename.

Return Value
There is no return value.

Comments
This procedure uses the EM_STREAMIN method to load the file into the rich edit control.


readline

readline proc source:DWORD,buffer:DWORD,spos:DWORD

Description
A procedure to read a line of text directly from memory.

Parameters
1.source The address of the memory to read the text from.
2.buffer The destination buffer to write the line of text to.
3.spos The current location pointer.

Return Value
The updated "spos" value is returned in EAX.
The line length not including zero or 13 is returned in ECX.

Comments
Readline copies a line of text from the source to the buffer starting from the offset set in "spos", updates the "spos" variable to the start of the following line of text and returns that variable in EAX. EAX returns ZERO if the end of the source is on the current line.

The length of the line not including ascii 0 and 13 is returned in ECX. You should test the buffer if ZERO is returned in EAX as it may contain the last line of text that is zero terminated.

Normally the "spos" variable is allocated before the procedure is called and initialised to zero. It is then updated after each call to the procedure.

Conditions to test for.
1. End of source returns zero in EAX.
2. blank line has 1st byte in buffer set to zero
and a line length in ECX of ZERO.
3. Line length is returned in ECX.


RichEd1

RichEd1 proc a:DWORD,b:DWORD,wd:DWORD,ht:DWORD,
             hParent:DWORD,instance:DWORD,ID:DWORD,WRAP:DWORD

RichEd2 proc a:DWORD,b:DWORD,wd:DWORD,ht:DWORD,
             hParent:DWORD,instance:DWORD,ID:DWORD,WRAP:DWORD

Description
Both procedures differ only in that they use different versions of the rich edit control.

Parameters
1. a Top X co-ordinate for control
2. b Top Y co-ordinate for control
3. wd Width to create control.
4. ht Height to creat control
5. hParent Parent handle of control.
6. hInstance The instance handle of the application.
7. ID The identification number of the control.
8. WRAP Specify if wordwrap is required, 0 = none, 1 = wordwrap.

Return Value
The return value is the handle of the control.

Comments
Note that you must use LoadLibrary and the name of the version of richedit control that you intend to use. For richedit 1, the name is RICHED32.DLL, for richedit 2, the name is RICHED20.DLL.


SaveFileDialog

SaveFileDialog proc hParent:DWORD,Instance:DWORD,lpTitle:DWORD,lpFilter:DWORD

Description
SaveFileDialog displays a common dialog to obtain the name of a file.

Parameters
1. hParent The handle of the parent window.
2. Instance The application or DLL instance handle.
3. lpTitle The address of a zero terminated string with the dialog title.
4. lpFilter The file pattern(s) to display in the dialog.

Return Value
The return value in EAX is the offset of a dedicated 260 byte buffer for this procedure. If the user enters a file name it will be written to the buffer, if the user cancels the dialog, the first byte in the buffer is set to ascii zero.

Comments
If the pattern is too long to place in the macro, it can be placed in a seperate variable and used in the macro.You should test for the user cancelling the operation by testing the 1st byte in the buffer that is returned in EAX with code similar to the following.

  mov patn, CTXT("all files",0,"*.*",0,"txt files",0,"*.txt;*.ini",0)
  mov fname, SaveFileDlg(hWin,hInstance,SADD("Save File ..."),patn)
  cmp BYTE PTR [eax], 0
  jne @F
  ; code to respond to cancelling the dialog here
@@:


SetClipboardText

SetClipboardText proc ptxt:DWORD

Description
Write text to the clipboard.

Parameters
ptxt Address of text to write to the clipboard. This can be the adress of a normal zero terminated string or you can use on of the masm32 macros for a direct string literal.

Return Value
This procedure has no return value.

Examples
invoke SetClipboardText,ADDR MyText
fn SetClipboardText,"Hi I am text being written to the clipboard"


shell

shell proc lpfilename:DWORD

Description
shell runs another process synchronously. It is designed to run programs sequentially in much the same manner as DOS batch files.

Parameter
1. lpfilename is the zero terminated string that contains the file name and any command line parameters that are required to follow it.

Return Value
The function has no return value.

Comments
This function runs another process synchronously and the calling application is disabled for the duration of the time that the other process runs. Care should be taken with this function to ensure that the processes being run closes properly otherwise the calling application will remain disabled.

Notes
This function emulates a very old DOS era function that ran an external executable file in a non-re-entrant monotasking environment and it is designed to be fail safe even on obscure hardware that is not always compatible with modern operating systems and may have suffered viral or similar damage. It comes at the price that it does not deallocate two handles used in a structure by the CreateProcess Windows API. The two handles are released when the application closes.

The problem was reproducable on an AMD K6-2 3D NOW processor running at 550 megahertz. The particular processor required a patch from Microsoft for the win95b version as it crashed when starting. When the procedure deallocated the two handles, the operating system locks up.

If you can find a reason to loop an executable at high speed under synchronous conditions you can use the shell_ex procedure that is a more modern design complete with priority control of the app to be started. Note that shell_ex and an alternative procedure wshell will crash on the test computer mentioned. The failure when looping the shell procedure occurs at about 10 thousand iterations under test conditions which is well beyond the design range of the original shell procedure.


shell_ex

shell_ex proc lpfilename:DWORD,process_priority:DWORD

Description
An extended version of the original "shell" procedure that accepts a parameter to change the priority of the child process.

Parameters
1.lpfilename The name of the executable file to run.
2.process_priority One of the values from the SetPriorityClass() API function call.

Return Value
There is no return value.

Comments
There is a risk on some version of win9x that the two API calls to free two handles associated with the CreateProcess() API will cause the machine to reboot. This does not appear to be a problem with the NT/2K/XP series of Windows OS versions.


Sorting Overview

Two sort designs are presented, one is a non recursive Quick Sort, the other is a design published in BYTE magazine in the early nineties called a Comb Sort. Both type have ascending and descending versions and are designed to sort DWORD size integers.

The non recursive quick sort is the faster of the two but the comb sort is well suited for smaller sorts up to about 50,000 items. Over this the extra speed of the quick sort will start to show. The comb sort is smaller code and a simpler design which is also more memory efficient so it may suite simpler applications.


StdErr

StdErr proc lpszText:DWORD

Description
Output text to the screen by the standard error handle.

Parameters
1. lpszText Zero terminated string to display to standard error.

Return Value
The return value is the byte count written to standard error.

Comments
This is an alternate method to display text to the console that can be used when STDOUT has been redirected to a file.


StdIn

StdIn proc lpszBuffer:DWORD,bLen:DWORD

Description
StdIn receives text input from the console and places it in the buffer required as a parameter. The function terminates when Enter is pressed.

Parameters
1. lpszBuffer The buffer to receive the text input from the console.
2. bLen The length of the buffer.

Return Value
There is no return value.

Comments
The console determines the length of the maximum buffer size. 128 bytes should handle most console input needs. The position of the input on the console can be set with the locate function.


StdOut

StdOut proc lpszText:DWORD

Description
StdOut will display a zero terminated string at the current position in the console.

Parameter
1. lpszText A zero terminates string.

Return Value
There is no return value.

Comments
There is no effective length limit on the string displayed. The position of the displayed text on the console can be set with the locate function.
The following macro will allow quoted text to be displayed at the current position on the console with the following syntax,

print "This is a test !"

print MACRO Quoted_Text:VARARG
  LOCAL Txt
  .data
    Txt db Quoted_Text,0
  .code
  invoke StdOut,ADDR Txt
ENDM


StripLF

StripLF proc strng:DWORD

Description
StripLF is designed to remove the CRLF (ascii 13,10) by writing an ascii zero in the place of the first occurrence of ascii 13.

Parameters
1. strng is the address of the buffer that needs to be truncated.

Return Value
The procedure has no return value.

Comments
This procedure was designed primarily for console mode input where and ascii 13,10 is appended to the end of the result. This effects entering numerical values that are converted from string to DWORD. Removing the CRLF allows the entered numbers to be converted correctly.


StripRangeI

StripRangeI proc lpszSource:DWORD,lpszDest:DWORD,stByte:BYTE,enByte:BYTE

Description
The StriprangeI function removes a range of characters from a zero terminated string that start with the stByte parameter and finish with the enByte parameter and writes the result to the lpszDest buffer address.

Parameters
1. lpszSource The address of the source buffer.
2. lpszDest The address of the destination buffer.
3. stByte The starting byte for the range to remove.
4. enByte The end byte for the range to remove.

Return Value
There is no return value.

Comments
For safety purposes, the destination buffer should be the same size as the source buffer. This function is ideally suited for removing html tags and the angle brackets that enclose them.


StripRangeX

StripRangeX proc lpszSource:DWORD,lpszDest:DWORD,stByte:BYTE,enByte:BYTE

Description
This function will remove a range of characters from the zero terminated string in lpszSource and place the result in the buffer lpszDest. The range is determined by the starting byte parameter stByte and the end byte parameter enByte. It does not remove the starting and ending byte characters.

Parameters
1. lpszSource The address of the source buffer.
2. lpszDest The address of the destination buffer.
3. stByte The starting byte for the range to remove.
4. enByte The end byte for the range to remove.

Return Value
There is no return value.

Comments
For safety purposes, the destination buffer should be the same size as the source buffer. This function will remove characters from between the two byte parameters ands is well suited for example at removing text withing brackets. ThisText(Enclosed Text) becomes ThisText() when the starting and ending bytes are "(" and ")".


StrLen

StrLen proc item:DWORD

Description
This function has been adapted from an algorithm written by Agner Fog. It reads the length of a zero terminated string and places it in eax. It is an unusual function in that it will read up to 3 bytes past the end of a buffer as it uses DWORD size reads. It appears that the condition does not generate a GP fault in windows as memory is usually alocated in 4 byte blocks.

Parameter
1. item The address of the zero terminaed string.

Return value
The length of the zero terminated string is returned in eax.

Comments
This function is measurably faster than a classic byte scanner and has its place where linear read speed is required.


StrToFloat

StrToFloatPROCstdcall public, szIn: PTR BYTE, fpout: PTR QWORD

Note that both parameters are DWORD size addresses.

Description
StrToFloat converts a floating point string to a floating point number.

Parameters
1. szIn The address of the floating point string.
2. fpout The address of the QWORD buffer to hold the result.

Return Value
If the procedure encounters an illegal character that it cannot convert, it returns the address of the character in eax.

Comment
It is the user's responsibility to ensure that there are no illegal characters in the szIn input string.


szappend

szappend proc string:DWORD,buffer:DWORD,location:DWORD

Description
Append zero terminated string data to end of string buffer.

Parameters
1. string The main buffer to append extra data to.
2. buffer The data to append to main buffer.
3. location The offset to write the append data to.

Return Value
The location of the end of the buffer which can be used for the next call to szappend as the "Location" parameter.

Comments
This algorithm is designed to repeatedly append zero terminated string data to the end of a user defined buffer. It uses a location pointer to save repeatedly scanning the buffer for the end position. With a new buffer, the first byte should be set to ascii zero, with an existing zero terminated string in a buffer, you should supply the length and set the location parameter to that length.
The return value is the buffer end position which you pass back to the procedure for the next appended data.


szCatStr

szCatStr proc lpszSource:DWORD, lpszAdd:DWORD

Description
szCatStr appends the second zero terminated string (lpszAdd) to the end of the first zero tereminated string (lpszSource). The result is zero terminated.

Parameters
1. lpszSource The address of the source string to be appended to.
2. lpszAdd The address of the string to append to lpszSource.

Return Value
There is no return value.

Comments
It is the users responsibility to ensure that the buffer for the source string is large enough to accept the appended string. Failure to do this will end up with a write page fault.


szCmp

szCmp proc str1:DWORD,str2:DWORD

Description
szCmp compares two zero terminated strings for difference.

Parameters
1. str1 The first string to compare
2. str2 The second string to compare

Return Value
If the two strings match, the return value is the length of the string. If there is no match, the return value is zero.

Comments
The procedure can be used on strings that may be of uneven length as the terminator will produce the mismatch even if the rest of the charactes match.


szCmpi

szCmpi proc src:DWORD, dst:DWORD, ln:DWORD

Description
A table driven high speed case insensitive text comparison algo.

Parameters
1. src The address of the first string to compare.
2. dst The address of the second string to compare
3. ln The number of charactes to test for, usually the length of the first string.

Return Value
szCmpi returns zero if the two strings or byte sequences are identical or the character count where the two byte sequences mismatch.

Comments
This procedure uses a character table and a character count and it can be used on any BYTE sequence including string. If you need to emulate the characteristics of the case sensitive version, convert both strings to a single case and then do a case sensitive comparison.


szCopy

szCopy proc src:DWORD, dst:DWORD

Description
szCopy copies a zero terminated string from the source buffer to the destination buffer.

Parameters
1. src The address of the source string
2. dst The address of the destination buffer

Return Value
There is no return value

Comments
The destination buffer must be large enough to hold the source string otherwise a page write fault will occur.


szLeft

szLeft proc lpSource:DWORD, lpDest:DWORD, lnth:DWORD

Description
szleft reads a set number of characters from the start of a zero terminated string and writes them to the destination buffer.

Parameters
1. source Address of the source string.
2. dest Address of the destination buffer.
3. lnth The number of characters to read.

Return Value
There is no return value.


szLen

szLen proc lpString:DWORD

Description
szLen reads the length of a zero terminated string and returns its length in eax.

Parameter
1. lpString Address of zero terminated string.

Return Value
The length of the zero terminated string without the terminating zero byte in eax.


szLower

szLower and szUpper

szLower proc text:DWORD
szUpper proc text:DWORD

Description
szLower converts any uppercase characters in the supplied zero terminated string to lowercase.
szUpper converts any lowercase characters in the supplied zero terminated string to uppercase.

Parameter
1. text The address of the text to convert.

Return Value
There is no return value.

Comments
szLower and szUpper works on the original string and writes it back to the same address.


szLtrim

szLtrim proc source:DWORD,dest:DWORD

Description
szLtrim trims the leading spaces and tabs from a zero terminated string and places the results in the destination buffer provided..

Parameters
1. source The address of the source string.
2. dest The address of the destination buffer.

Return Value
The return value is the length of the trimmed string which can be zero.

Comments
If the string is trimmed to zero length if it has no other characters, the first byte of the destination adress will be ascii zero. Ensure the destination buffer is big enough to receive the substring, normally it is advisable to make the buffer the same size as the source string. If your design allows for overwriting the string, you can use the same string address for both source and destination.


szMid

szMid proc source:DWORD, substring:DWORD, stPos:DWORD, ln:DWORD

Description
szMid reads a set number of characters from a set starting position in the source string and writes them to the destination string.

Parameters
1. source Address of source string.
2. substring Address of buffer to receive the substring.
3. stPos Start position of first character.
4. ln The number of bytes to read.

Return Value
There is no return value.

Comments
It is the users responsibility to ensure that the length of the substring is fully contained within the source string. Failure to do so will result in either a read or write page fault.


szMonoSpace

szMonoSpace proc src:DWORD

Description
Format a string with single spaces only replacing any tabs with spaces and trimming tabs and spaces from either end of the string.

Parameters
1. src The address of the zero terminated string to format.

Return Value
The return value is the address of the source string passed to the procedure.

Comments
The algorithm removes any leading tabs and spaces then formats the string with single spaces replacing any tabs in the source with spaces. If there is a trailing space after formatting, the string is truncated to remove it.


szMultiCat

szMultiCat proc C pcount:DWORD,lpBuffer:DWORD,args:VARARG

Description
szMultiCat uses a buffer that can be appended with multiple zero terminated strings, this is more efficient when multiple strings need to be concantenated.

Parameters
1. pcount is the number of zero terminated strings to append.
2. lpBuffer is the address of the buffer to appends the strings to.
3. args is the comma seperated parameter list.

Return Value
This function does not return a value.

Comments
The allocated buffer must be large enough to accept all of the appended zero terminated strings. The parameter count must match the number of zero terminated strings.


szRemove

szRemove proc src:DWORD,dst:DWORD,remv:DWORD

Description
szRemove removes a substring from a source string and writes the result in the destination buffer.

Parameters
1. src The address of the source string
2. dst The address of the destination buffer
3. remv The address of the substring to remove

Return Value
The destination address is returned in the EAX register. This is mainly useful for writing a macro using this procedure.

Comments
The procedure supports using a single buffer for both the source and destination if the original string does not need to be preserved.


szRep

szRep proc src:DWORD,dst:DWORD,txt1:DWORD,txt2:DWORD

Description
Replace text in a zero terminated string.

Parameters
1. src The address of the source to replace text in.
2. dst The destination buffer for the results.
3. txt1 The text to replace.
4. txt2 The text to replace it with.

Return Value
The procedure has no return value.

Comments
While the text replacement technique is unproblematic, the memory strategy for the destination buffer needs to be properly thought out to get reliable operation. If the replacement is the same length as the text to replace or shorter, the destination buffer can safely be made the same length as the source buffer but if the replacement text is longer, a method to calculate the extra size of the destination buffer must be used.

The szWcnt procedure is one way of calculating the extra length required in the destination buffer. The technique is to calculate the additional length of the replacement word, subtract the original text length from it then multiply the result by the number of occurrences of the replacement text.

Example
Here is a working example of both replace methods.

@@:
  mov lwrd1, len(word1)
  mov lwrd2, len(word2)
  mov eax, lwrd2

.if lwrd1 >= eax
; --------------
; simple replace
; --------------
  add lsrc, 16384
  mov hsrc, alloc$(lsrc) ; allocate src and dst the same length
  mov hdst, alloc$(lsrc)
  invoke SendMessage,hEdit,EM_GETSELTEXT,0,hsrc ; get the selected text
  invoke szRep,hsrc,hdst,word1,word2 ; perform replacement on its contents
  invoke SendMessage,hEdit,EM_REPLACESEL,TRUE,hdst ; replace the selection in the editor
  free$ hdst
  free$ hsrc
  ret

.else
; ---------------
; complex replace
; ---------------
  add lsrc, 16384
  mov hsrc, alloc$(lsrc)
  invoke SendMessage,hEdit,EM_GETSELTEXT,0,hsrc ; get the selected text
  mov wcnt, rv(szWcnt,hsrc,word1) ; count the first word in source
  mov eax, lwrd2
  sub eax, lwrd1 ; calculate extra word2 length in eax
  invoke IntMul,wcnt,eax ; multiply word count by extra bytes
  add lsrc, eax ; add it to the source length
  mov hdst, alloc$(lsrc) ; allocate the larger size memory
  invoke SendMessage,hEdit,EM_GETSELTEXT,0,hsrc
  invoke szRep,hsrc,hdst,word1,word2
  invoke SendMessage,hEdit,EM_REPLACESEL,TRUE,hdst
  free$ hdst
  free$ hsrc

.endif


szRev

szRev proc lpszSource:DWORD,lpszDest:DWORD

Description
szRev reverses a zero terminated string in lpszSource and places it in lpszDest.

Parameters
1. lpszSource The address of the source string.
2. lpszDest The address of the destination buffer.

Return Value
There is no return value.

Comments
The destination buffer must be at least the size of the source buffer otherwise a read page fault will occur.


szRight

szRight proc source:DWORD, dest:DWORD, lnth:DWORD

Description
szRight reads a set number of characters from the end of a zero terminated string and writes them to the destination buffer.

Parameters
1. source Address of the source string.
2. dest Address of the destination buffer.
3. lnth The number of characters to read.

Return Value
There is no return value.


szRtrim

szRtrim proc source:DWORD,dest:DWORD

Description
szRtrim trims the trailing spaces and tabs from a zero terminated string and places the results in the destination buffer provided..

Parameters
1. source The address of the source string.
2. dest The address of the destination buffer.

Return Value
The return value is the length of the trimmed string which can be zero.

Comments
If the string is trimmed to zero length if it has no other characters, the first byte of the destination adress will be ascii zero. Ensure the destination buffer is big enough to receive the substring, normally it is advisable to make the buffer the same size as the source string. If your design allows for overwriting the string, you can use the same string address for both source and destination.


szTrim

szTrim proc src:DWORD

Description
szTrim trims leading and trailing tabs and spaces from a zero terminated string.

Parameter
1. src The address of the zero tereminated string.

Return Value
The return value is the length of the trimmed string which can be zero.

Comments
If the string is trimmed to zero length if it has no other characters, the first byte of the destination adress will be ascii zero. This procedure acts on the original source string and overwrites it with the result.


szWcnt

szWcnt proc src:DWORD,txt:DWORD

Description
Count the number of instances of a specified text in a zero terminated string.

Parameters
1. src The address of the zero terminated string.
2. txt The specified zero terminated text to count.

Return Value
The return value is the number of instances of the text to count.

Comments
This procedure among other things is used to calculate the extra length for an output buffer when replacing text with other text that is longer than the original text.


testreg

testreg proc

Description
testreg tests zero terminated string to see if they are registers.

Parameters
1. The string address is passed in the EAX register

Return Values
Not a register         0
Segment register       1   cs ds es ss fs gs
8 bit register         2   al ah bl bh cl ch dl dh
16 bit register        3   ax bx cx dx si di sp bp
32 bit register        4   eax ebx ecx edx esi edi esp ebp

Comments
This procedure is designed for very high speed word recognition of registers. It support both upper and lower case but not mixed case. It is used in applications that process assembler source code to test if an operand is a register or not.


tstline

tstline proc lpstr:DWORD

Description
This is a dedicated procedure to test the contents of a line of text loaded by the readline or writeline procedures or their matching macros linein$ or lineout$.

Parameters
1.lpstr The address of the string to test.

Return Value
If the return value is ZERO, the line of text has no useful content.
If the return value is not ZERO, it is the ascii number of the first character zero extended into EAX.

Comments
This procedure scans the string stripping leading spaces or tabs until it find either a character above ascii 32 (space) which it returns zero extended in EAX or alternatively if the first character after stripping any leading spaces or blanks is below ascii 32, it returns zero.

If the return value is non zero, it can be tested either as a DWORD against an immediate number or alternatively it can be tested as a BYTE in AL against another register or memory operand.


ucappend

ucappend proc buffer:DWORD,string:DWORD,cloc:DWORD

Description
ucappend appends the characters in "string" to the buffer "buffer" and returns the current location "cloc" so it can be used for the next append operation.

Parameters
  buffer = the buffer to append characters onto
  string = the characters to append to the buffer
  cloc   = the current append location POINTER

  NOTE that cloc POINTER is a BYTE counter. To get the UNICODE character count, divide "cloc" by 2.

Return Value
The return value is the current location pointer that is to be used for the next append operation.

Comments
This procedure is designed for high speed sequential append operations by avoiding the necessity of rescanning the string each iteration to find the end. The "cloc" argument allows the procedure to directly find the end of the existing characters so that it can write the next text data to the end of the buffer.

NOTE that the buffer to append the text data to must be large enough to hold all of the data being appended to it.

    LOCAL buffer[260]:TCHAR
    LOCAL bptr  :DWORD
    LOCAL str1  :DWORD
    LOCAL str2  :DWORD
    LOCAL str3  :DWORD
    LOCAL cloc  :DWORD

    mov bptr, ptr$(buffer)

    mov str1, chr$("one ")
    mov str2, chr$("two ")
    mov str3, chr$("three ")

    mov cloc, 0    ; start at the beginning of the buffer

    invoke ucappend,bptr,str1,cloc
    mov cloc, eax

    invoke ucappend,bptr,str2,cloc
    mov cloc, eax

    invoke ucappend,bptr,str3,cloc
    mov cloc, eax

This is a simple example, the procedure would normally be used in a loop where the variable "cloc" is updated each iteration of the loop.


ucArgByNum

ucArgByNum proc src:DWORD,dst:DWORD,num:DWORD

Description
ucArgByNum returns a user selected argument from a line of text if it exists.

Parameters
  src = string to get argument from
  dst = buffer to take selected argument
  num = 1 based number for argument, 1 = arg1, 2 = arg2 etc ...

Return Value
The return value is the user nominated argument number if the argument exists or ZERO if no argument is available.

Comments
Test EAX to determine if the nominated argument exists.

    test eax, eax
    jz no_arg_label


ucCatStr

ucCatStr proc wstr1:DWORD,wstr2:DWORD

Description
Append one unicode string to another.

Parameters
1.wstr1 The source string to append to.
2.wstr2 The string to append to it.

Return Value
There is no return value.

Comments
The source buffer must be large enough to accept the additional string appended to it.


ucCmdTail

ucCmdTail proc

Description
ucCmdTail returns the address of the command line tail if it exists..

Parameters
This procedure does not receive any arguments.

Return Value
The return value is the address of the command tail if it exists.

Comments
If you need to further modify the string returned by this procedure you should copy it to a buffer of its own so you do not alter the original command line string.

cst yourbuffer, cmdtail_return string_address
or
invoke ucCopy,cmdtail_return string_address,yourbuffer


ucCmp

ucCmp proc wst1:DWORD,wst2:DWORD

Description
Compare two unicode strings.

Parameters
1.wstr1 The first string to test
2.wstr2 The second string to test

Return Value
If the two strings do not match, the return value is ZERO otherwise the length of the two strings is returned.

Comments
NOTE: The returned string length on match is in CHARACTERS, not BYTES.


ucCopy

ucCopy proc wsrc:DWORD,wdst:DWORD

Description
Copy unicode string from one memory buffer to another.

Parameters
1.wsrc The address of the source string
2.wdst The address of the destination buffer

Return Value
There is no return value.

Comments
The destination buffer must be large enough to hold the source string.


ucFind

ucFind proc sPos:DWORD, wsrc:DWORD, wsub:DWORD

Description
Find a unicode substring in a unicode source string.

Parameters
1. sPos The required starting position in the source string.
2.wsrc The source string to be searched.
3. wsub The substring to find in the source string.

Return Value
If substring is not found, the return value is ZERO otherwise the starting position for the substring is returned.

Comments
The starting position and the return value if the substring is found are BOTH 1 (one) based indexes. The first character in the source buffer is at position ONE, not zero.


ucGetCL

ucGetCL proc obuf:DWORD,ccnt:DWORD,argnum:DWORD

Description
ucGetCL reads the length of a unicode string in characters.

Parameters
obuf   = user supplied output buffer
ccnt   = output buffer character count
argmun = the 1 based arg the user wants 1 = arg1, 2 = arg2 etc ....

Return Value
< 0 = buffer not large enough for selected arg
  0 = arg not found
> 0 = arg number read from command tail

Comments
This algorithm provides double buffer protection, it allocates memory based on the command tail length so the length cannot be overrun and it allocates the same length buffer for the user selected argument. When the argument is obtained from the "ucArgByNum" procedure, its length is checked against the length of the user supplied buffer and rejected if it is longer. The technique is designed to prevent deliberate command line exploits.

If you use an .IF block to evaluate EAX, ensure that you use SDWORD PTR before EAX as the return value can be nagative if the user supplied buffer is not large enough.

    .if SDWORD PTR eax < 0
      ; do something
    .else
      ; do default
    .endif


ucgetline

ucgetline proc src:DWORD,dst:DWORD,cloc:DWORD

Description
ucgetline reads the line of UNICODE text at the current location pointer. ( cloc )

Parameters
src  = text to get line from.
dst  = the buffer to receive the line if it exists.
cloc = the current location pointer.

Return Value
The return value is either the current location pointer for the next line "cloc" OR zero if no argument is available.

Comments
This procedure is used for tasks like reading a line of text at a time from a text file and placing it in a user defined buffer. NOTE that the text must be UNICODE text, it will not work on ASCII text.

    __UNICODE__ equ 1
    ...................

    LOCAL cloc  :DWORD
    LOCAL ptxt  :DWORD

    mov ptxt, chr$("line 1",13,10,"line 2",13,10,"line 3",13,10,"line 4",13,10)

    mov cloc, 0

  lbl:
    mov cloc, rv(ucgetline,ptxt,pbuf,cloc)
    cmp cloc, 0
    je @F
    print pbuf,13,10
    jmp lbl

  @@:


ucLeft

ucLeft proc wsrc:DWORD,wdst:DWORD,ccnt:DWORD

Description
ucLeft read a preset number of characters from the left side of the source string and write them to the destination buffer.

Parameters
1.wsrc The source string to read the characters from.
2.wdst The destination buffer.
3.ccnt The count of characters to copy to the destination buffer.

Return Value
There is no return value.

Comments
The destination buffer must be large enough to hold the number of characters read from the source buffer.


ucLen

ucLen proc lpwstr:DWORD

Description
ucLen reads the length of a unicode string in characters.

Parameters
1.lpwstr The address of the string to get the character count from.

Return Value
The return value is the character count.

Comments
The character count returned does NOT include the terminating zero.


ucLower

ucLower proc wsrc:DWORD

Description
ucLower converts a unicode string to lower case.

Parameters
1. wsrc The address of the string to convert.

Return Value
There is no return value.

Comments
This procedure is a wrapper for the API function CharLowerBuffW


ucLtrim

ucLtrim proc wsrc:DWORD,wdst:DWORD

Description
ucLtrim removes leading spaces from the left side of a unicode string.

Parameters
1. wsrc The source string to read the data from.
2. wdst The destination string to write the result to.

Return Value
There is no return value.

Comments
The destination buffer must be large enough to receive the results.


ucMid

ucMid proc wsrc:DWORD,wdst:DWORD,stPos:DWORD,ln:DWORD

Description
ucMid read a preset number of characters from a user defined starting point in a source string and writes the result to a destination buffer.

Parameters
1. wsrc The source string to read the data from.
2. wdst The destination buffer.
3. stPos The starting position to read from.
4. ln The number of characters to read.

Return Value
There is no return value.

Comments
The destination buffer must be large enough to receive the result.


ucMonoSpace

ucMonoSpace proc src:DWORD

Description
ucMonoSpace cleans up a string by trimming junk off each end and setting the spacing to single spaces..

Parameters
1.src = The address of the string to clean up.

Return Value
The return value is the address of the modified string passed to the procedure.

Comments
This procedure trims tabs and spaces from each end of "src" and replace any duplicate tabs and spaces with a single space. The result is written back to the source string address.


ucMultiCat

ucMultiCat proc C pcount:DWORD,lpBuffer:DWORD,args:VARARG

Description
ucMultiCat concantenates multiple unicode strings to a buffer that may contain other unicode string data.

Parameters
1. pcount The number of strings to append to the buffer.
2. lpBuffer The address of the destination buffer.
3. args A variable number of string addresses whose count has been set in "pcount".

Return Value
The procedure returns the address of the destination buffer so it can be used with a macro.

Comments
This procedure uses the C calling convention because it can handle a variable number of parameters. The destination buffer must be large enough to hold ALL of the strings being appended to it. If the buffer does not already have unicode string data, the first character position must be set to ZERO so that the data is written to the beginning of the buffer. Care should be taken to ensure that the "pcount" argument matches the number of string to be appended.


ucOpenFileDialog

ucOpenFileDialog proc hParent:DWORD,Instance:DWORD,lpTitle:DWORD,lpFilter:DWORD

Description
A File Open common dialog that takes and returns unicode string data.

Parameters
1.hParent The handle of the window that is calling the dialog.
2.Instance The application's hInstance member.
3.lpTitle A unicode string to use as the dialog's title.
4.lpFilter A unicode format control string for the file types to display.

Return Value
The return value is the address of the buffer that holds the file name. If no file name was selected, the first character in the buffer will be ZERO.

Comments
The buffer that is returned will be overwritten by the next call to the dialog so if the data is required it must be stored in another buffer before calling the procedure again.


ucRemove

ucRemove proc src:DWORD,dst:DWORD,remv:DWORD

Description
Remove every occurrence of a user defined string from a source string and write the result to the destination buffer.

Parameters
src  = the source string to remove text from.
dst  = the destination buffer for the result.
remv = the string  to remove from the "src" string.

Return Value
The destination address is the return value.

Comments
This algorithm produces a shorter string than the source if any text is removed so a destination buffer of the same length as the source can safely be used.


ucRep

ucRep proc src:DWORD,dst:DWORD,txt1:DWORD,txt2:DWORD

Description
Replace every occurrence of text in a source string and write its results to the destination string.

Parameters
src  = the source string to perform replacements in.
dst  = the destination buffer to write the results to.
txt1 = the text to replace.
txt2 = the text to replace it with.

Return Value
Return Value

Comments
NOTE : This algorithm does NOT perform any memory management on the destination buffer size. For simple replacements where the replacement text is the same length or shorter than the text it replaces you can safely use a buffer of the same length but if the replacement is longer than the text it replaces you need to make the destination buffer larger to handle the extra characters. With simple tasks you can just use a much larger destination buffer but for complex tasks you need to calculate the extra length required. The ucWcnt algorithm is designed to do this.

The technique is to do the simple arithmetic to get the extra character count for each replacement then multiply it by the number of occurrences of the string to replace. It is both useful and easy enough to perform to add a safety margin to the calculated buffer size.

In pseudo notation.
-----------------------------------------

slen1 = length(str1)
slen2 = length(str2)

If slen2 > slen1
  extra = slen2 - slen1                 ; calculate the length difference
  extra = extra * wordcount(srcstring)  ; multiply it by the word count in the source
  extra = extra + 1024                  ; add some padding
  bufferlen = sourcelen + extra         ; add the extra to the source length
Else
  bufferlen = sourcelen                 ; just allocate a buffer of the same size
EndIf

memory = memalloc(bufferlen)

-----------------------------------------


ucRev

ucRev proc wsrc:DWORD,wdst:DWORD

Description
Reverses a unicode string and write the result to a buffer.

Parameters
1.wsrc The string to reverse.
2.wdst The buffer to write the result to.

Return Value
There is no return value.

Comments
The destination buffer must be at least the size of the source buffer.


ucRight

ucRight proc wsrc:DWORD,wdst:DWORD,ccnt:DWORD

Description
Read a preset number of characters from the right side of the source string and write the data to a destination buffer.

Parameters
1.wsrc The address of the source string.
2.wdst The address of the destination buffer.
3.ccnt The number of characters to copy.

Return Value
There is no return value.

Comments
The destination buffer must be large enough to hold the results.


ucRtrim

ucRtrim proc wsrc:DWORD,wdst:DWORD

Description
Remove trailing spaces from a unicode string and write result to a destination buffer

Parameters
1.wsrc Source string to test.
2.wdst Destination buffer for result.

Return Value
There is no return value.

Comments
The destination buffer must be large enough to receive the result.


ucSaveFileDialog

ucSaveFileDialog proc hParent:DWORD,Instance:DWORD,lpTitle:DWORD,lpFilter:DWORD

Description
A Save File common dialog that returns unicode string data.

Parameters
1.hParent The handle of the window that is calling the dialog.
2.Instance The application's hInstance member.
3.lpTitle A unicode string to use as the dialog's title.
4.lpFilter A unicode format control string for the file types to display.

Return Value
The return value is the address of the buffer that holds the file name. If no file name was selected, the first character in the buffer will be ZERO.

Comments
The buffer that is returned will be overwritten by the next call to the dialog so if the data is required it must be stored in another buffer before calling the procedure again.


ucUpper

ucUpper proc wsrc:DWORD

Description
ucUpper converts a unicode string to uper case.

Parameters
1.wsrc The address of the source string to convert.

Return Value
There is no return value.

Comments
This procedure is a wrapper for the API CharUpperBuffW


ucWcnt

ucWcnt proc src:DWORD,txt:DWORD

Description
Count the number of occurrences of "txt" in "src".

Parameters
src = the source address to search.
txt = the text to search for.

Return Value
The return value is the number of occurrences of "txt" in "src".

Comments
This algorithm has various uses but one of its important uses is to count the number of occurrences of a string in the source when performing replacements that are longer than the text they replace.


udw2str

udw2str proc dwNumber:DWORD, pszString:DWORD

Description
udw2str converts an UNSIGNED DWORD to a string.

Parameters
1. dwNumber The unsigned DWORD to convert.
2. pszString The buffer to receive the result.

Return Value
There is no return value.

Comments
This algorithm is designed for unsigned DWORD input only.


ustr2dw

ustr2dw proc pszString:DWORD

Description
ustr2dw converts a zero terminated string to an UNSIGNED DWORD.

Parameter
1. pszString The address of the zero terminated string to convert.

Return Value
The unsigned DWORD is returned in EAX.

Comments
This procedure is designed for unsigned DWORD values only.


VerticalTile

VerticalTile proc hWin:DWORD,bmpID:DWORD,cnt:DWORD

Description
VerticalTile tiles a bitmap in the client area of a window from top down to the number of repeats set in the function call.

Parameters
1. hWin The handle of the window that has the tiled bitmap in its client area.
2. bmpID The resource ID number for the bitmap to be tiled.
3. cnt The number of repeats of the bitmap from top down.

Return Value
There is no return value

Comments
This procedure allows a small bitmap to be tiled vertically to cover the client area of a window, it is suitable for WEB style tiling and it allows image data to be displayed at a much smaller file size than a full client area size bitmap.


WordCount

WordCount proc startpos:DWORD,
               lpSource:DWORD,srcLngth:DWORD,
               lpSubStr:DWORD,subLngth:DWORD

Description
This algorithm is a Boyer Moore design that counts the number of occurrences of the substring in the source data. It can be used for both text and binary data.

Parameters
1. startpos The zero based starting position in the source data.
2. lpSource The address of the data to be searched.
3. srcLngth The length of the source data to be searched.
4. lpSubStr The address of the substring to be counted.
5. subLngth The length of the substring to be counted.

Return Value
Zero for no match or the number of occurrences in the source data of the substring.

Comments
The starting position should always be less than the length of the source minus the length of the pattern being counted.


wordreplace

wordreplace proc src:DWORD,dst:DWORD,wrd1:DWORD,wrd2:DWORD

Description
Globally replace whole words in the source text and write the result to the destination.

Parameters
1.src The source text to replace words in.
2.dst The destination buffer for the result.
3.wrd1 The word to replace.
4.wrd2 The words to replace it with.

Return Value
There is no return value.

Comments
This procedure is a table based linear text scanner based on the following allowable characters.

characters ! # $ % & ? @ _
numbers 0123456789
upper case ABCDEFGHIJKLMNOPQRSTUVWXYZ
lower case abcdefghijklmnopqrstuvwxyz

The procedure will recognise whole words made up of the above characters and will replace every instance of that word with the replacement text. It is suited for simple tasks like replacing whole words in text such as in a text editor but it is also fast enough to loop through a number of words and replace all of them in a macro built into a scripting language or similar application.
It is an interim technology for tasks smaller than those normally handled by a far more complex hash table.


wrd2bin_ex

wrd2bin_ex proc var:WORD,buffer:DWORD

Description
A high speed WORD to binary format converter.

Parameters
1.var The WORD size variable to convert.
2.buffer The address of the destination buffer.

Return Value
There is no return value.

Comments
This algorithm is suitable for streaming binary output as high speed.


write_disk_file

write_disk_file proc lpName:DWORD,lpData:DWORD,fl:DWORD

Description
write_disk_file writes the content of a memory buffer to a disk file

Parameters
1. lpName The address of a zero terminated string that contains the file name.
2. lpData The address of the buffer that contains the data to write.
3. fl The number of bytes to write to the file.

Return Value
The return value is the number of bytes written if the procedure succeeds or zero if it fails.

Comments
This procedure is designed to write a complete disk file each time it is called. It will overwrite an existing file of the same name.


Write_To_Disk

Write_To_Disk proc hEdit:DWORD,lpszFileName:DWORD

Description
Write_To_Disk writes the contents of a richedit control to a diskfile specified in the second parameter.

Parameters
1. hEdit The rich edit control to read from.
2. lpszFile Name The zero terminated disk file name.

Return Value
This procedure has no return value.

Comments
This procedure uses the EM_STREAMOUT method to write the contents of a rich edit control to a disk file.


writeline

writeline proc source:DWORD,buffer:DWORD,spos:DWORD,flag:DWORD

Description
An algorithm that writes a line of text to a memory buffer and updates the last write position.

Parameters
1.source The address of the text to write to the buffer.
2.buffer The buffer to write to.
3.spos The current write location pointer.
4.flag Select if a CRLF is appended to the text.
Zero = appended CRLF.
Non zero = no CRLF appended.

Return Value
EAX returns the updated "spos" location pointer.
ECX returns the number of BYTES written.

Comments
This algorithm is useful for writing text files directly to memory so the result can be written in one disk write. Normally the "spos" variable is allocated before the procedure is called, initialised to zero and updated each time the procedure returns with the new value.


wshell

wshell proc lpfilename:DWORD

Description
An alternative method of running an external executable file.

Parameters
1.lpfilename The name of the executable file to run.

Return Value
There is no return value.

Comments
This procedure has been included because a few people were very vocal in their demand for changes to the original reliable version of "shell". This version is neither recommended nor supported and it may cause early version of Windows to reboot on certain non standard hardware.

NOTE that the original version of "shell" is the recommended version, even though it has a minor memory leak by not closing the two handles associated with CreateProcess(). The memory is reclaimed when the application closes.

These considerations may no longer be applicable for OS versions from win2000 upwards.


wtok

wtok proc pText:DWORD,pArray:DWORD

Description
Tokenise words within text "in place" and return an array of pointers to each token. The algorithm supports MASM style alternate quotations.

Parameters
1. pTxt The address of the source text to tokenise.
2. pArray The address of a DWORD variable that will be used for the handle of the array of pointers. Please refer to the comments section for further details.

Return Value
The return value in EAX is the number of tokens in the array of pointers.

Comments
When the address of the variable for the pointer array is passed to the procedure, the procedure in turn writes the address of the allocated memory back to that address so that within the scope of the procedure that allocated the variable and calls the tokeniser, the variable is then the direct pointer to the array of pointers. When the pointer array is no longer needed the variable should be deallocated using GlobalFree() within the same scope as the variable was allocated. The MASM32 macro "free" works correctly for this task.

Example
LOCAL MyVar :DWORD
Pass ADDR MyVar to the tokeniser.
Use MyVar as the address of the array of pointers after the tokeniser has returned.
free MyVar

Note : This algorithm is designed to be modified by experienced programmers in terms of the character range in the table to control the contents of words to be tokenised. The single and double quotations should not be changed as the algorithm uses them internally. If you are familiar enough with an algorithm of this type, you can selectively remove either the single or double quotation support in specialised applications.


XorData

XorData RolData RorData

XorData proc lpSource:DWORD,ln:DWORD,lpKey:DWORD,lnKey:DWORD
RolData proc lpSource:DWORD,ln:DWORD,lpKey:DWORD,lnKey:DWORD
RorData proc lpSource:DWORD,ln:DWORD,lpKey:DWORD,lnKey:DWORD

Description
The three procedures are used in the identical manner, they differ only in the sequence to decrypt the encrypted data. XorData will decrypt data encrypted by itself using the same key. RolData and RorData are symetrical pairs where one will decrypt data encrypted by the other.

Parameters
1. lpSource The address of the source data to encrypt.
2. ln The length of the source data.
3. lpKey The address of the key data use to encrypt the source data.
4. lnKey The length of the key data.

Return Value
These procedures do not return a value.

Comments
The data for both the source and key are capable of having non printable characters including ascii zero which means the procedures must have the correct lengths in the parameters. Failure to set the correct lengths will result in general protection faults from either reading or writing past the end of the source or key.