Logitech Modula-2 v3.4

This commit is contained in:
davidly 2024-07-02 07:25:31 -07:00
parent 20ea3e7590
commit c411c69691
305 changed files with 200618 additions and 0 deletions

View File

@ -0,0 +1,45 @@
(*$S-*)
(*$R-*)
(*$T-*)
MODULE e;
FROM InOut IMPORT WriteLn, WriteInt, WriteCard, WriteString;
CONST
DIGITS = 200;
VAR
high, n, x : CARDINAL;
a : ARRAY [ 0..DIGITS ] OF CARDINAL;
BEGIN
high := DIGITS;
x := 0;
n := high - 1;
WHILE n > 0 DO
a[ n ] := 1;
n := n - 1;
END;
a[ 1 ] := 2;
a[ 0 ] := 0;
WHILE high > 9 DO
high := high - 1;
n := high;
WHILE 0 <> n DO
a[ n ] := x MOD n;
x := 10 * a[ n - 1 ] + x DIV n;
n := n - 1;
END;
IF x >= 10 THEN WriteCard( x, 2 ) ELSE WriteCard( x, 1 ); END;
END;
WriteLn;
WriteString( "done" );
WriteLn;
END e.

View File

@ -0,0 +1,35 @@
/* everything imported must be declared as far */
/* use 'far' or compile with /AL */
#include "rtsm2exi.h"
extern far pascal IntegerProcedure();
extern int far extInt;
extern far pascal StringProcedure1();
extern far pascal StringProcedure2();
/* locals do not have to be declared as far */
char *localString;
main()
{
/* everything that is passed to Modula-2 must be far */
/* use 'far' or compile with /AL */
char far *stringParam;
printf("Start in C\n");
IntegerProcedure(extInt); /* init of module -> extInt still 0 */
IntegerProcedure(extInt); /* init module passed -> extInt is 10 */
stringParam="string declared in C, length 31";
StringProcedure1(31, stringParam);
StringProcedure2(stringParam);
localString="End in C\n";
printf(localString);
/* exit the program with m2exit */
m2exit(0);
}

View File

@ -0,0 +1,27 @@
echo off
echo.
echo Example of a main program in C that calls procedures in Modula-2.
echo.
echo Before executing this command file, make sure that both Logitech
echo Modula-2 and Microsoft C 5.1 are properly installed. This batch
echo file assumes that the name of Microsoft C small-model library is
echo "SLIBCER.LIB" and that it is accessible through the "SET LIB="
echo environment setting.
echo.
echo (Note: if you have purchased only the Compiler Pack, you must
echo change the "m2l" command in this file to the corresponding "link"
echo command for DOS.)
echo.
pause
set m2sav=%m2lib%
echo on
set m2lib=%m2lib%;%lib%
cl /c main.c
m2c mod.def mod
m2l main mod /case /p /lib cmrts slibcer
rem link main mod,,,..\..\m2lib\lib\cmrts ..\..\m2lib\lib\m2lib slibcer;
main
pause
echo off
set m2lib=%m2sav%
set m2sav=

View File

@ -0,0 +1,15 @@
FOREIGN C DEFINITION MODULE Mod;
TYPE
StringPointer = POINTER TO ARRAY [0..100] OF CHAR;
VAR
extInt : INTEGER;
PROCEDURE IntegerProcedure(x : INTEGER);
PROCEDURE StringProcedure1(s : ARRAY OF CHAR);
PROCEDURE StringProcedure2(p : StringPointer);
END Mod.

View File

@ -0,0 +1,60 @@
IMPLEMENTATION MODULE Mod;
FROM Terminal IMPORT WriteLn, WriteString;
FROM InOut IMPORT WriteInt;
PROCEDURE IntegerProcedure(x : INTEGER);
VAR local : INTEGER;
BEGIN
local := x;
WriteString("IntegerProcedure, param : ");
WriteInt(x,5);
WriteLn;
WriteString(" local : ");
WriteInt(local,5);
WriteLn;
END IntegerProcedure;
PROCEDURE StringProcedure1(s : ARRAY OF CHAR);
BEGIN
WriteString("StringProcedure1, param : ");
WriteString(s);
WriteLn;
END StringProcedure1;
MODULE LocalModule[1];
IMPORT WriteString, WriteLn, StringPointer;
EXPORT StringProcedure2, localdata;
VAR localdata : INTEGER;
PROCEDURE LocalProcedure(s : ARRAY OF CHAR) : INTEGER;
VAR localvar : INTEGER;
BEGIN
WriteString("LocalProcedure, param : ");
WriteString(s);
WriteLn;
localvar := 12;
RETURN localvar;
END LocalProcedure;
PROCEDURE StringProcedure2(p : StringPointer);
BEGIN
WriteString("StringProcedure2, param : ");
WriteString(p^);
WriteLn;
END StringProcedure2;
BEGIN
localdata := LocalProcedure("Init of local module");
END LocalModule;
BEGIN
extInt := 10;
WriteString("Init of Mod, extInt : ");
WriteInt(extInt,5); WriteLn;
WriteString(" localdata : ");
WriteInt(localdata,5); WriteLn;
END Mod.

View File

@ -0,0 +1,26 @@
This example shows a simple program in C that calls Modula-2 procedures.
Special attention has to be given to the following points:
- Modula-2 handles only far code and far data. Use the 'far' keyword in
C for all data and procedures handled also in Modula-2, or compile with
the C compiler option /AL to use the large memory model.
- C doesn't provide real string variables. Strings are handled with
pointers to an array of characters. Use pointers also in Modula-2
or use the knowledge about the implementation and pass the string
length along with the pointer.
- The bodies of the Modula-2 modules will only be executed at the beginning
of the first call to a Modula-2 procedure. Avoid using any module bodies.
If you do, be aware that the initialization of the module won't occur
before the first call.
- The program must exit by calling the function "m2exit()". This function
will properly exit the program by executing the Modula-2 library and
RTS termination procedures.
The function prototype for this function is available in the C include
file "rtsm2exi.h". You should "#include" this file at the beginning
of any C modules that need to call the "m2exit()" function.

View File

@ -0,0 +1,77 @@
MODULE Corou;
FROM SYSTEM IMPORT PROCESS , ADDRESS , NEWPROCESS ,
TRANSFER ;
FROM Terminal IMPORT WriteString , WriteLn ;
FROM Storage IMPORT ALLOCATE ;
FROM Keyboard IMPORT KeyPressed ;
FROM RTSMain IMPORT Status , Terminate ;
CONST
WorkSpaceSize = 8000; (* process workspace size *)
VAR
main ,
coroutine1 ,
coroutine2 ,
coroutine3 : PROCESS;
workSpacePtr1 ,
workSpacePtr2 ,
workSpacePtr3 : ADDRESS;
PROCEDURE Message1;
BEGIN
LOOP
WriteString ("In Coroutine # 1");
WriteLn;
TRANSFER (coroutine1, coroutine2);
END;
END Message1;
PROCEDURE Message2;
BEGIN
LOOP
WriteString ("In Coroutine # 2");
WriteLn;
TRANSFER (coroutine2, coroutine3);
END;
END Message2;
PROCEDURE Message3;
BEGIN
LOOP
WriteString ("In Coroutine # 3");
WriteLn;
IF KeyPressed() THEN
WriteLn;
WriteString("Done!");
WriteLn;
Terminate(Normal);
END;
TRANSFER (coroutine3, coroutine1);
END;
END Message3;
BEGIN (* main *)
(* allocate the workspaces *)
ALLOCATE(workSpacePtr1, WorkSpaceSize);
ALLOCATE(workSpacePtr2, WorkSpaceSize);
ALLOCATE(workSpacePtr3, WorkSpaceSize);
(* create the new processes *)
NEWPROCESS(Message1, workSpacePtr1, WorkSpaceSize, coroutine1);
NEWPROCESS(Message2, workSpacePtr2, WorkSpaceSize, coroutine2);
NEWPROCESS(Message3, workSpacePtr3, WorkSpaceSize, coroutine3);
(* start the job *)
TRANSFER(main, coroutine1);
END Corou.

View File

@ -0,0 +1,19 @@
echo off
echo.
echo Before executing this command file, make sure that Logitech Modula-2
echo has been properly installed.
echo.
echo This batch file will compile, link, and execute the coroutines
echo example (refer to the manual for more information on coroutines).
echo To end the execution of the example program, press any key.
echo.
echo (Note: if you have purchased only the Compiler Pack, you must
echo change the "m2l" command in this file to the corresponding "link"
echo command for DOS.)
echo.
pause
echo on
m2c corou
m2l corou/o/p
rem link corou,,,..\..\m2lib\lib\m2rts ..\..\m2lib\lib\m2lib;
corou

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,37 @@
Start Stop Length Name Class
00000H 001B9H 001BAH COROU_TEXT CODE
001BAH 001DEH 00025H ASCII_TEXT CODE
001DFH 0027BH 0009DH DISPLAY_TEXT CODE
0027CH 00534H 002B9H DOSMEMORY_TEXT CODE
00535H 00738H 00204H DynMem_TEXT CODE
00739H 008A0H 00168H KEYBOARD_TEXT CODE
008A1H 00BF9H 00359H STORAGE_TEXT CODE
00BFAH 00FDFH 003E6H TERMBASE_TEXT CODE
00FE0H 011A6H 001C7H TERMINAL_TEXT CODE
011A7H 0126DH 000C7H RTSError_TEXT CODE
0126EH 0129CH 0002FH RTSError_INIT_TEXT CODE
0129DH 019D1H 00735H RTSMain_TEXT CODE
019D2H 01A84H 000B3H RTSLanguage_TEXT CODE
01A85H 01A85H 00001H RTSLanguage_INIT_TEXT CODE
01A86H 01C1AH 00195H RTSCoroutine_TEXT CODE
01C1BH 01C1BH 00001H RTSCoroutine_INIT_TEXT CODE
01C1CH 01CF1H 000D6H MODULE_TABLE_DATA FAR_DATA
01CF2H 01D02H 00011H INIT_FLAG_DATA FAR_DATA
01D04H 01ED3H 001D0H RTSMain_DATA FAR_DATA
01ED4H 01ED7H 00004H RTSCoroutine_DATA FAR_DATA
01ED8H 01EF3H 0001CH COROU_DATA FAR_BSS
01EF4H 01EF4H 00000H ASCII_DATA FAR_BSS
01EF4H 01EF4H 00000H DISPLAY_DATA FAR_BSS
01EF4H 01EF4H 00000H DOSMEMORY_DATA FAR_BSS
01EF4H 01F7BH 00088H KEYBOARD_DATA FAR_BSS
01F7CH 01F9DH 00022H STORAGE_DATA FAR_BSS
01F9EH 02030H 00093H TERMBASE_DATA FAR_BSS
02032H 02033H 00002H TERMINAL_DATA FAR_BSS
02040H 03F7FH 01F40H STACK STACK
03F80H 03F80H 00000H FREE FREE_BSS
Origin Group
01ED:0 DGROUP
Program entry point at 0129:03D6

View File

@ -0,0 +1,8 @@
ntvdm -r:..\.. -e:m2sym=c:\m2lib\sym ..\..\m2exe\M2C.EXE corou
rem the modula 2 linker fails
rem ntvdm -r:..\.. -e:m2lib=m2lib\lib ..\..\m2exe\m2l corou/o/p
rem the qbx linker works fine
ntvdm -r:..\.. -e:lib=c:\m2lib\lib ..\..\link corou,,,m2lib m2rts.lib;

View File

@ -0,0 +1,27 @@
DEFINITION MODULE ANSIScreen;
(* In order to use this module the driver ANSI.SYS needs to be
installed. This can be achieved by inserting the command
DEVICE=ANSI.SYS in the CONFIG.SYS file of your computer. *)
PROCEDURE GotoXY (colon, line : CARDINAL);
(* positions the cursor at the given colon and line *)
PROCEDURE ClrScr;
(* the screen is erased and the cursor set in the top left corner *)
PROCEDURE SetAttribute (attr : CHAR);
(* all subsequent writing on the screen will use the given attribute
until it is changed by further calls to this procedure. Any
combination of attributes can be obtained by calling SetAttribute
multiple times. *)
CONST
(* here are the possible attribute: *)
Normal = '0';
Bold = '1';
Underline = '4';
Blink = '5';
Reverse = '7';
Concealed = '8';
END ANSIScreen.

View File

@ -0,0 +1,33 @@
IMPLEMENTATION MODULE ANSIScreen;
FROM Terminal IMPORT Write, WriteString;
FROM CardinalIO IMPORT WriteCardinal;
CONST ESC = 33C;
PROCEDURE GotoXY (colon, line : CARDINAL);
(* positions the cursor at the given colon and line *)
BEGIN
Write (ESC); Write ('[');
WriteCardinal (line,0);
Write (';');
WriteCardinal (colon,0);
Write ('H');
END GotoXY;
PROCEDURE ClrScr;
(* the screen is erased and the cursor set in the top left corner *)
BEGIN
Write (ESC); WriteString ('[2J');
Write (ESC); WriteString ('[H');
END ClrScr;
PROCEDURE SetAttribute (attr : CHAR);
(* all subsequent writing on the screen will use the given attribute
until it is changed by further calls to this procedure. Any
combination of attributes can be obtained by calling SetAttribute
multiple times. *)
BEGIN
Write (ESC); Write ('['); Write (attr); Write ('m');
END SetAttribute;
END ANSIScreen.

View File

@ -0,0 +1,47 @@
MODULE DigClock;
FROM ANSIScreen IMPORT
ClrScr, GotoXY, SetAttribute, Reverse, Normal;
FROM TimeDate IMPORT
GetTime, TimeToString, Time;
FROM Terminal IMPORT
KeyPressed, Write, WriteString, Read;
CONST CornerX = 29; (* X coordinate of upper left corner *)
CornerY = 15; (* Y coordinate of upper left corner *)
SecPos = 16; (* index of the seconds in the string *)
VAR actualTimeDate : Time;
ch, oldSeconds : CHAR;
timeString : ARRAY [0..17] OF CHAR;
BEGIN (* Example2 *)
ClrScr;
SetAttribute (Reverse);
GotoXY (CornerX, CornerY); WriteString ("ÉÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ»");
GotoXY (CornerX, CornerY+1); WriteString ("º º");
GotoXY (CornerX, CornerY+2); WriteString ("ÈÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍͼ");
SetAttribute (Normal);
GotoXY (54,25); (* set cursor to bottom right corner *)
WriteString (" press any key to exit...");
oldSeconds := ' '; (* set to any non-digit *)
REPEAT
GetTime (actualTimeDate);
TimeToString (actualTimeDate, timeString);
IF timeString[SecPos] <> oldSeconds THEN
(* update screen only if seconds have changed *)
GotoXY (CornerX+2, CornerY+1);
WriteString (timeString);
(* place a separation between date and time: *)
SetAttribute (Reverse);
GotoXY (CornerX+10, CornerY+1);
Write (' ');
SetAttribute (Normal);
GotoXY (80,25); (* get cursor out of way *)
oldSeconds := timeString[SecPos];
END;
UNTIL KeyPressed();
Read (ch); (* clear the keyboard buffer *)
ClrScr; (* and the screen *)
END DigClock.

View File

@ -0,0 +1,20 @@
echo off
echo.
echo Before executing this command file, make sure that Logitech Modula-2
echo has been properly installed.
echo.
echo This batch file will compile, link, and execute the ANSI screen
echo example. NOTE: this program requires that you have the DOS ANSI.SYS
echo device driver installed in your CONFIG.SYS file (refer to your DOS
echo manual for more details).
echo.
echo (Note: if you have purchased only the Compiler Pack, you must
echo change the "m2l" command in this file to the corresponding "link"
echo command for DOS.)
echo.
pause
echo on
m2c ansiscre.def ansiscre digclock
m2l digclock/o/p
rem link digclock,,,..\..\m2lib\lib\m2rts ..\..\m2lib\lib\m2lib;
digclock

View File

@ -0,0 +1,101 @@
MODULE FileIO;
(* Program to demonstrate basic file I/O *)
FROM Terminal IMPORT Read, ReadAgain, ReadString, WriteString, WriteLn, Write;
FROM CardinalIO IMPORT ReadCardinal, WriteCardinal;
FROM LogiFile IMPORT File, Open, OpenMode, ReadChar, WriteChar, EndFile,
EOL, Close, Delete, Create;
CONST ESC = 33C;
VAR ch : CHAR;
linesToCopy, linesCopied : CARDINAL;
inFile, outFile : File;
ok : BOOLEAN;
PROCEDURE SpecifyFile (VAR file : File;
mode : OpenMode;
prompt : ARRAY OF CHAR;
VAR result : BOOLEAN);
VAR fileName : ARRAY [0..80] OF CHAR;
ch : CHAR;
done : BOOLEAN;
BEGIN
result := FALSE;
REPEAT
WriteLn;
WriteString (prompt);
ReadString (fileName);
WriteLn;
ReadAgain; Read (ch); (* read the terminating character *)
IF ch=ESC THEN RETURN END; (* allow to quit the program *)
Open (file, fileName, mode, done);
IF mode <> ReadOnly THEN
IF done THEN
(* the output file exists already *)
WriteString (" --- exists already. delete (y/-) ? ");
Read (ch); Write (ch); WriteLn;
done := FALSE;
IF CAP (ch) = 'Y' THEN
Delete (file, done);
END;
IF NOT done THEN RETURN END;
END;
Create (file, fileName, done);
END;
IF NOT done THEN
WriteString (" --- cannot open the file"); WriteLn;
END;
UNTIL done; (* keep trying until open is successful *)
result := TRUE;
END SpecifyFile;
BEGIN (* Example3 *)
WriteString (" This program copies the specified number of lines from ");
WriteLn;
WriteString (" the input file to the output file and to the screen. ");
WriteLn;
SpecifyFile (inFile, ReadOnly, "Enter input file name:", ok);
IF NOT ok THEN RETURN END;
WriteString ("Lines to copy> ");
ReadCardinal (linesToCopy);
Read(ch); (* read terminator of ReadCardinal *)
IF ch=ESC THEN
Close (inFile, ok);
RETURN; (* allow to quit the program at any moment *)
END;
SpecifyFile (outFile, WriteOnly, "Enter output file name:", ok);
IF ok THEN
linesCopied := 0; ch := EOL;
WriteLn;
LOOP
IF ch = EOL THEN
IF linesCopied >= linesToCopy THEN EXIT END;
INC (linesCopied);
WriteCardinal (linesCopied,4); WriteString (": ");
END;
ReadChar (inFile, ch); (* Read from input file, *)
IF EndFile (inFile) THEN EXIT END; (* check for EOF, otherwise *)
WriteChar (outFile, ch); (* copy the char to the file *)
Write (ch); (* and to the screen. *)
END; (* LOOP *)
WriteLn;
IF linesCopied < linesToCopy THEN
WriteString("[Only ");
WriteCardinal(linesCopied,0);
WriteString(" lines in file]"); WriteLn;
ELSE
WriteCardinal(linesCopied,0);
WriteString (" lines copied");
END; (* IF *)
Close (outFile, ok);
END; (* IF *)
Close (inFile, ok);
END FileIO.

View File

@ -0,0 +1,17 @@
echo off
echo.
echo Before executing this command file, make sure that Logitech Modula-2
echo has been properly installed.
echo.
echo This batch file will compile, link, and execute the file I/O example.
echo.
echo (Note: if you have purchased only the Compiler Pack, you must
echo change the "m2l" command in this file to the corresponding "link"
echo command for DOS.)
echo.
pause
echo on
m2c fileio
m2l fileio/o/p
rem link fileio,,,..\..\m2lib\lib\m2rts ..\..\m2lib\lib\m2lib;
fileio

View File

@ -0,0 +1,25 @@
int far extInt=10;
char* s = "IntegerProcedure, param is %u \n";
void far pascal IntegerProcedure (x)
int x;
{
printf (s,x);
};
void far pascal StringProcedure1 (x,string)
int x;
char* far string;
{
printf (string);
printf (" length received : %u \n",x);
};
void far pascal StringProcedure2 (string)
char* far string;
{
printf (string);
printf ("\n");
};

View File

@ -0,0 +1,16 @@
FOREIGN C DEFINITION MODULE c;
TYPE
StringPointer = POINTER TO ARRAY [0..50] OF CHAR;
VAR
extInt : INTEGER;
PROCEDURE IntegerProcedure (x : INTEGER);
PROCEDURE StringProcedure1 (s : ARRAY OF CHAR);
PROCEDURE StringProcedure2 (s : StringPointer);
END c.

View File

@ -0,0 +1,28 @@
MODULE main;
FROM Terminal IMPORT WriteString, WriteLn;
FROM SYSTEM IMPORT ADR;
FROM c IMPORT
IntegerProcedure,
StringProcedure1,
StringProcedure2,
extInt;
VAR
local : INTEGER;
modulastring : ARRAY [0..50] OF CHAR;
BEGIN
local := 10;
modulastring := "String declared in Modula-2, length 39";
WriteString("Start in Modula-2");WriteLn;
IntegerProcedure(extInt);
IntegerProcedure(local);
StringProcedure1(modulastring);
StringProcedure2(ADR(modulastring));
WriteString("End in Modula-2");WriteLn;
END main.

View File

@ -0,0 +1,31 @@
echo off
echo.
echo Example of a main program in C that calls procedures in Modula-2.
echo.
echo Before executing this command file, make sure that both Logitech
echo Modula-2 and Microsoft C 5.1 are properly installed. This batch
echo file assumes that the name of Microsoft C large-model library is
echo "LLIBCER.LIB" and that it is accessible through the "SET LIB="
echo environment setting.
echo.
echo (Note: if you have purchased only the Compiler Pack, you must
echo change the "m2l" command in this file to the corresponding "link"
echo command for DOS.)
echo.
pause
rem (compile the C program with /AL when using library routines with
rem large data)
set m2sav=%m2lib%
echo on
set m2lib=%m2lib%;%lib%
cl /c /AL c.c
m2c c.def main
m2l main c /case /p /lib mcrts llibcer
rem link main c,,,..\..\m2lib\lib\mcrts ..\..\m2lib\lib\m2lib llibcer;
main
pause
echo off
set m2lib=%m2sav%
set m2sav=

View File

@ -0,0 +1,14 @@
This example shows a simple program in Modula-2 with calls to C procedures.
Special attention has to be given to the following points:
- Modula-2 handles only far code and far data. Use the 'far' keyword in
C for all data and procedures used also in Modula-2, or compile with the
C compiler option /AL to use the large memory model.
- C doesn't provide real string variables. Strings are handled with
pointers to arrays of characters. Use pointers also in Modula-2 or
use the knowledge about the implementation and pass the string
length along with the pointer.

Binary file not shown.

Binary file not shown.

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,227 @@
Logitech Modula-2 Release 3.40 March, 1990
----------------------------------------------------------------------------
This file documents the major differences in the compiler, linker, and
utilities between Release 3.03 and Release 3.40.
Compiler
========
The Modula-2 Compiler included in Release 3.40 has undergone extensive
work since Release 3.03. This section documents some of the changes
that have been made.
* The compiler now provides 21-28% faster compilation.
* Mixed-language support has been greatly improved. Some of the
changes include:
- Procedures called from C or Pascal will restore registers
DS, DI, and SI.
- Before calling a C or Pascal procedure DS will be loaded
with the segment descriptor of DGROUP.
- The RTS has been updated to allow you to debug programs
that contain C or Pascal procedures, or that have main
programs written in C.
See the examples in the EXAMPLES\MOD-C and EXAMPLES\C-MOD
directories for more information.
* The default options of the compiler have been changed. Tests
are now off by default, and all optimizations are on.
* For debugging, use "/DEBUG". The /DEBUG option now forces the
"/SYM" option.
* The default options for the compiler must now be set with an
environment variable, M2COPT (the M2C.CFG file is no longer
used). For example, to set the tests on by default, use:
SET M2COPT=/T+/R+/S+/F+
* LONGINT constants can now be specified by a trailing "L". For
example,
var := VAL(LONGINT, 1234);
may now be specified as
var := 1234L;
* The compiler now supports non-standard priority levels (levels
greater than 7). See the Priority Levels section at the end
of this document for information about modifying the RTS for
greater priority level support.
* All known bugs in the compiler have been fixed.
Compiler Implementation Notes
-----------------------------
* After installing Release 3.40, you should recompile and relink
your program. Release 3.40 is completely source and library
compatible with Release 3.0 (so no source modifications have
to be made). Note: Release 3.40 is also completely compatible
with Release 3.0 .SYM files, so it is not necessary to recompile
your definition modules.
* In this version of the compiler, two-dimensional arrays are
always allocated on even boundaries.
Linker
======
The M2L linker included in Modula-2 Release 3.40 has undergone extensive
enhancements since Release 3.03. This section documents the changes that
have been made.
* Support for Microsoft languages
The M2L linker can now be used to link Microsoft C and
Microsoft MASM code, as well as Logitech Modula-2. It also
supports the linking of mixed Modula-2 and C programs as
described in Chapter 6 of the User's Manual (as well as
demonstrated in the example programs provided with Release
3.40).
* Other enhancements
* M2L now supports GROUP definitions and references, the
ORG statement, absolute symbols, absolute segments, and
external near self-relative fixups, as well as many
previously unsupported Microsoft record types and object
format extensions.
* M2L can link programs that are up to 40% larger than
than could be linked with the Release 3.03 linker, and
when linking programs it can operate up to 30% faster
than M2L 3.03.
* If M2L terminates with an error, it now sets the DOS
ERRORLEVEL code to 3. In the case of an "insufficient
memory" error it is set to 2.
* M2L options changes and enhancements
* M2L now understands an environment variable, M2LOPT. It
reads and processes this environment variable before it
processes the rest of the command line. This is useful
for setting default link options. For example:
SET M2LOPT=/o/p
will set the default options to optimize and pack the
output executable file.
* Several new options have been introduced, and some defaults
have been changed:
* The output of M2L V3.03 and previous versions was quite
verbose. A new option, /VERBOSE (or /V) has been added
to M2L to enable the output of this linker information.
By default the output is not verbose.
* A new switch, /DEBUG (or /DEB) has been added. This
switch corresponds to the compiler /DEB option. When
linking a program for debugging, specify the /DEBUG
option on the command line (or in the M2LOPT environment
variable).
* MAP files are no longer generated by default. Use the
/MAP (or /DEBUG) option to generate a .MAP file.
Utilities
=========
All of the utilities have undergone extensive user-interface changes
and improvements. The look and operation of these programs may be
somewhat different than that described in the Toolkit manual, but
the overall result of the program's operation is the same.
M2Vers
------
The M2Vers 3.40 version utility now operates 20-30% faster than
M2Vers 3.03. A new option, /I, controls the display of version
change statistics information. If "/I+" is selected, the statistics
information is displayed. The default is "/I-". In addition, line
numbers are displayed for errors and warnings, to allow you to more
easily locate the problem in the source file.
M2Decode
--------
The M2Decode utility now generates mixed source by default, and will
automatically generate a decode backup file (.DBK) instead of prompting
for different output files. The decode output is now combined in one
single .DEC output file. Several enhancements have been made to the
overall look and operation of M2Decode; included is a "percentage of
completion" counter that comes in quite handy when decoding large
object modules.
M2Make
------
M2Make now supports automatic building of overlays with a new command
syntax. To completely build a program that uses overlays, you specify
it with a syntax similar to M2L. For example, if you had a program
"Base", and it contained two overlays, "Ovl1" and "Ovl2", and "Ovl2"
contained an overlay "Ovl3", you could easily "make" the entire program
by using this command:
M2Make Base(Ovl1+Ovl2(Ovl3))
This command generates a CMDFILE.BAT that will automatically compile and
link the files necessary to build the entire application (including the
overlays).
Note: The syntax for generating overlays with M2Make is similiar to but
reversed from the syntax for generating overlays with M2L.
M2Check
-------
M2Check now supports a batch-mode option, "/B". If you want to
execute M2Check from a batch file, specify "/B+" after the file
name argument. For example:
M2Check TEST.MOD/B+
The default setting of the "/B" option is "/B-".
Libraries
=========
All known bugs in each of the libraries have been fixed.
The Debuggers and the POINT Editor
==================================
For information on the changes to the Run-Time and Post-Mortem Debuggers,
refer to the file DEBUGGER.DOC. For information on changes to the POINT
Editor, refer to the file POINT.DOC.
Priority Levels Enhancement
===========================
The compiler now supports the compilation of programs containing priority
levels greater than seven (a maximum of 16 levels are now supported). The
supplied RTS, however, only supports a maximum priority level of seven.
If you wish to use the greater number of priority levels, you must modify
the RTS so that it can properly support the larger priority levels.
Logitech Modula-2 Technical Support can not provide you with any support
regarding any modifications you make to the RTS. For more information,
see the file RTSREAD.ME in the M2LIB\RTS directory.

View File

@ -0,0 +1,341 @@
Logitech Modula-2 Release 3.40 March, 1990
----------------------------------------------------------------------------
The Logitech Modula-2 Release 3.40 Debuggers
============================================
The Run-Time and Post-Mortem Debuggers included in Modula-2 Release 3.40
have undergone extensive enhancements since Release 3.03. This section
documents the changes that have been made.
Overview of New Features
------------------------
Details of these new features are described in the following section.
* A new "Breakpoint" window has been added that lists the current
breakpoints and their associated information (i.e. breakpoint
address, count, etc.). It also allows the user to select and
view a breakpoint's position in the Text window.
* A new "decOde" window has been added which allows the user to
view the assembly decode of an address, and to manipulate
breakpoints at the assembly decode level.
* If a configuration file has not been found, the user is now
prompted for the number of lines desired (25 or 43).
* Several new options and commands have been added.
Debugger Options
----------------
* The Run-Time Debugger no longer uses the RTDPAR.CFG file as described
in the Toolkit manual. Instead, it allows you to define the default
values for the debugger options by means of the DOS environment
setting "M2RTD".
For example, you might want to include a command like the following
into your DOS AUTOEXEC.BAT file:
SET M2RTD=/Q-/Z-/H:40/S-/B-/M-/D+/G-/V-/P:"D:"/A:"MAP"/J:1C,21/F-
In addition, all RTD options are now also available on the command
line.
The PMD now also allows you to set default values for its options in
the same way by means of the DOS environment string "M2PMD". For a
list of the PMD options please refer to the Modula-2 User's Manual.
* The RTD no longer supports the options /L and /W. Instead, it provides
the option /H (described below) which is simpler to use and understand
than /L and /W. The /H option allows you to specify the RTD heap space
size in kilobytes (KB).
* The RTD and PMD now support a "library file" option, /F. This option
directs the debuggers to read a library control file that contains a
list of library modules. Commands in this library control file allow
you to control the default step mode and storage of procedure information
in the debugger module window list.
* The RTD now supports an "overlay" option, /O=number. This option
directs the debugger to stop at a particular overlay in the application,
allowing you to execute over a particular number of overlays.
Run-Time Debugger Option Details
--------------------------------
This is a complete list of the options available in the Run-Time Debugger
included in Release 3.40.
/A (default: /A:"MAP")
Specification of the MAP file extension
/B (default: /B-)
Big swap
When "/B+" is specified, the application program is removed
from memory while in a breakpoint (it is swapped out to disk).
Note: this could lead to unexpected effects when an application
interrupt occurs (the code of the interrupt hanlder is no longer
in memory). To prevent such problems, the options /K, /I, or /J
should be used for all interrupts handled by the application.
/D (default: /D+)
Application screen (see description in manual)
/F (default: /F-)
Library file
If "/F+" is specified, the file DB.LBR is read. This file
contains a list of the names of library modules and commands.
The commands in this library file allow you to control the
default step mode and storage of procedure information in the
debugger module list. In the .LBR file, each library module
must be specified on a separate line using the following format:
MODULE = <module name> [s[+,-]] [p[+,-]]
where "s" means "Step" and "p" means "Procedure". The defaults
for the switches are "s+" and "p-". When "s" is set, the
corresponding module will have the step mode disabled by default.
When "p" is set, all procedure information for the module is
removed from the internal heap of the debugger. While this
disables symbolic debugging for that module, it saves memory
in the internal heap of the debugger.
The search strategy for this file is the same as for the files
of the application: current directory, master path of the
application, and paths in the M2LBR environment string.
Note that for library modules, the debuggers do not prompt the
user for a file name when the REF or source file for the module
is not found automatically.
/G (default: /G-)
Graphics screen (see description in manual)
/H (default: /H- if /S- and /B-
/H:64 if /S+ or /B+)
Heap space size in kilobytes (KB)
This option specifies the size of the heap used by the RTD.
A heap overflow error will occur in the RTD if it needs
more heap memory than was specified with /H. If this option
is not specified, then the heap of the RTD is only limited by
the free memory available from the DOS operating system. When
the swap options (/S or /B) are used, the /H option is always
set by default.
The heap used by the RTD for a minimal program is in the
order of about 10 KB. The RTD needs about 84 bytes of
heap space per module and 16 bytes per procedure of the
application program. Depending on its structure, 10 to 20KB
may be needed for storing information on the call chain,
on data structures, and on breakpoints. Breakpoint tables
may consume a significant amount of memory when using Go
Statement or Go Flat to step through in large procedures.
The command 'Free Heap' in the status or help window may be
used to understand the amount of heap space used by the RTD.
If a module is marked with "p-" in the file DB.LBR (see
option /F above), the heap space allocated initially for the
procedures of this module will be freed and reused.
/I (default: not set)
List of interrupt vectors to be handled by a dummy
handler while in the RTD (e.g. /I:1C,8)
By means of the /I option it is possible to set an interrupt
vector to a dummy interrupt service routine while execution is
taking place in the RTD.
The syntax of the /I option is:
/I=hh,hh,hh (where h is an hexadecimal digit)
The list can have a maximum of 16 elements (vectors). The
keyboard (as well as the mouse and timer) interrupt should
not be disabled in the RTD, otherwise the corresponding device
cannot be used in the RTD anymore.
/J (default: not set, except for vector 1B)
Interrupt vectors to be replaced by original (DOS, RTD)
interrupt handlers while in the RTD (e.g. /J:1C,21)
By means of the /J option it is possible to set an interrupt
vector to its original value while in the RTD. The original
value is the value this vector had when the RTD was invoked.
The syntax of the /J option is:
/J=hh,hh,hh (where h is an hexadecimal digit)
The list can have a maximum of 16 elements (vectors). The RTD
always includes interrupt 1BH (IBM-PC/DOS Ctrl+Break) implicitly
into the list of vectors associated with option "/J".
/K (default: not set)
Interrupt mask to be used by the RTD (e.g. /K:A0)
By means of the /K option it is possible to specify an interrupt
mask which is used by the RTD while in a breakpoint.
The syntax of the /K option is:
/K=hh (where h is an hexadecimal digit)
The mask A0, for instance, disables the printer as well as the
alternate printer. The mask 01 disables the timer interrupt, etc.
The keyboard (as well as the mouse and timer) interrupt should
not be disabled in the RTD, otherwise the corresponding device
cannot be used in the RTD anymore.
/M (default: /M-)
Mouse (see description in manual)
/O=n (default /O-)
Overlay count
This option allows you to specifies the number of overlays in
which the RTD will not stop.
/P (default: /P:"D:")
Drive and path for temporary files (see description in manual)
/Q (default: /Q-)
Query (see description in manual)
/S (default: /S-)
Small swap
When "/S+" is specified, the application program is removed
from memory while in a breakpoint (it is swapped out to disk).
Note: this could lead to unexpected effects when an application
interrupt occurs (the code of the interrupt hanlder is no longer
in memory). To prevent such problems, the options /K, /I, or /J
should be used for all interrupts handled by the application.
/V (default: /V-)
Virtual disk (memory disk) for temporary RTD files
The drive and directory path for the "/V+" option are defined
by the "/P" (see above).
/Z (default: /Z-)
Use page zero for the RTD (see options /D and /G also)
New Commands in the Debuggers
-----------------------------
* A new "Free Heap" command "F" is present in both the Status and
Help windows. This command shows the amount of free memory currently
available when in the RTD (or PMD). If none of the memory control
options are selected (/H, /S, or /B), then the free heap will also
include the free memory available from the DOS operating system.
This command can be useful in order to find an optimal value to
specify with the /H option (described above).
* The Text window now contains a "Decode" command "D". This command
shows the code address of the selected line in the Text window and
updates the display of the "decOde" window to that address.
* The decOde window contains several new commands:
- it now contains a "Decode" command "D". When this command
is executed, you are prompted to enter an address to begin
the assembly decode at.
- it now contains a "Registers" command "R". When this command
is executed, the current values of the registers and flags
are displayed.
- it now contains both "Go Line" and "Go Breakpoint" commands
("GL" and "GB"). These commands operate in the same manner
as their equivalents in the Text window. The "Go Line" command
can also be executed by a double click on the desired line in
the decOde window.
- it now contains the "Set Breakpoint", "Clear Breakpoint", and
"Kill all Breakpoint" commands ("S", "C", and "K"). These
commands operate in the same manner as their equivalents in
the Text window, but only on breakpoints in the decOde window.
Breakpoints set in both the decOde window and the Text window
will appear in the decOde window.
Enhancements
------------
* The decOde window now supports the decoding of 80x87 and 80186
instructions.
* When loading and unloading overlays, the module selected in the
"Module" window is now always the main module of the current overlay.
* The RTD now supports the debugging of applications that have been
linked with the M2L optimize option.
* The RTD now preserves the interrupt controller mask used by the
application program.
Display Configuration
---------------------
The default display configuration file provided for the debuggers is
for the monochrome display adapter. If you are using a CGA, EGA, or
VGA display, you may wish to change the default display configuration.
Simply change to your M2\M2EXE directory and copy the appropriate
configuration file for your adapter to the debugger configuration
file DB.CFG:
Display Adapter Configuration File
--------------- ------------------
MDA MDA.CFG
CGA CGA.CFG
EGA EGA.CFG
VGA EGA.CFG
For example, if you are using an EGA adapter, you should copy the
file EGA.CFG to DB.CFG:
C:
CD \M2\M2EXE
COPY EGA.CFG DB.CFG
Additional Notes
----------------
* The RTD and Interrupt Handling
If an interrupt occurs that is handled by an IOTRANSFER in the
application program being debugged while the program is stopped
at a breakpoint, the system will hang. In order to prevent this,
one of the /I, /K, or /J options (described above) should be
used for each interrupt handled with IOTRANSFER in the application
program. This is not necessary if it is known that the interrupt
will not occur while the program is stopped in the debugger.
When debugging applications using the Logitech Modula-2 Real Time
Kernel, then the interrupt vectors 8H (the timer interrupt) and 21H
(the DOS call interrupt) should always be in the list of vectors
specified with the /J option.
* Debugging "Non-Debuggable" Programs
The current version of the debuggers do not support the debugging
of programs that have not been compiled and linked for debugging.
When you try debugging a program that cannot be debugged, the
program will execute as normal, without giving the debugger
control.

View File

@ -0,0 +1,267 @@
Logitech Modula-2 Release 3.40 March, 1990
----------------------------------------------------------------------------
The Logitech Modula-2 POINT Editor 2.01
=======================================
The POINT Editor has had extensive improvements made to it since version
1.52. This file describes some of these improvements, and how to get
started with the new version. Information in this document replaces
any equivalent information in the existing POINT manual.
Version 2.01
------------
The user interface for version 2.01 has been extensively enhanced to
allow for simple and complete keyboard usage, without the use of the
"mouse simulation" commands found in version 1.52 and earlier. The
complete functionality of POINT can now be accessed easily through the
keyboard (as well as with the mouse). In addition to the new user
interface, many bugs found in the previous versions have been fixed,
and overall operation has been improved.
Quick Start
-----------
* To execute POINT, enter "PT" at the DOS prompt. To load a file,
press the F2 key to display the file selection screen. You may
use the cursor arrow keys (or the mouse), or enter the name of
the file you wish to edit. Press the Enter key to load the file.
* Notice the highlighted letters in the menus. These are "speed keys"
that can be executed by pressing and holding the Alt-key in
conjunction with the highlighted letter. For example, the "Files"
menu has the letter "F" highlighted. So, in order to view the Files
menu, simply press "Alt-F".
* Inside each menu there are highlighted letters and optional direct
keys listed to perform each specific command. For example, notice
the first entry in the Files menu:
"Open File Full F2"
The "F" in "Full" is highlighted, indicating that it is the speed
key within the menu for performing that command. The "F2" function
key also will perform that command. The cursor up and down arrow
keys (in conjunction with the Enter key) may also be used to select
a command. So, in this case, from the editor screen, pressing
"Alt-F-F" (or F2) will open a file into a full screen window.
Experiment with the different menus and speed keys to get a feel
for their operation.
* The highlighted letters in the file selection screen and the color
settings screen operate in the same manner. For example, pressing
"Alt-E" in the file selection screen will execute the "New pattern"
command.
* For context-sensitive help on a particular command or menu, press
the "F1" function key. You may now navigate through the help system
via the menus on each help screen.
* Some quick-key commands:
Esc - returns you to the current editing screen
from any process in POINT
F3 - saves all the files you currently have on
screen and returns you to DOS
F10 - abandons all changes you have made to your
files and returns you to DOS
Alt-Q - lets you choose which files you want to save
and which files you want to abandon, and
then returns you to DOS
POINT 2.01 Files Included
-------------------------
Here is a list of the POINT 2.01 files included in Logitech Modula-2
Release 3.40:
* PT.EXE - the POINT executable program file.
* PT.INI - the default initialization file.
* PTCOLOR.INI - color initialization file. If you have been
using a monochrome monitor, and now a color
monitor, copy PTCOLOR.INI into PT.INI.
* PTM2COLR.INI - color initialization file for use with the
Logitech Modula-2 Development System 3.4.
* PTMONO.INI - monochrome initialization file. If you have
been using a color monitor, and now a
monochrome monitor, copy PTMONO.INI into
PT.INI.
* PTM2MONO.INI - monochrome initialization file for use with
the Logitech Modula-2 Development System 3.4.
* PTEXPERT.INI - "expert" user initialization file.
* PT.ASC - ASCII Reference Table file. This file can be
opened in your POINT editing session for
quick visual reference, a basis for character
search, or for inclusion into your edited
file.
* PT.HLP - the help file, used by POINT to give an
extensive summary and detailed description
of commands and menus.
* PT.MSG - the message file, used by POINT to give one
line of help for each command.
* M2ASSIST.INI - template initialization file, for use with
Logitech Modula-2 Development System 3.4.
* M2ASSIST.HLP - help file for use with the M2Assist system.
Point 2.01 Command Number Reference
-----------------------------------
Here is the complete list of command numbers supported by POINT 2.01.
These commands may be used in all key and menu definitions in the POINT
initialization file. Refer to your POINT manual for details.
No. POINT Command
--- -------------
0 Reserved for internal use.
1 Reserved for internal use.
2 Copy the current selection to the duplicate mode insertion point.
3 Move the current selection to the extract mode insertion point.
4 Move the current selection to the scrap buffer.
5 Verify edited files to be saved; then exit to the operating system.
6 Reserved for internal use.
7 Define a new window; then load file.
8 Move insertion point to the beginning of the file.
9 Move insertion point to the end of the file.
10 Redraw the entire POINT screen.
11 Toggle window between full size and less-than-full size.
12 Place this window on the top of the stack of windows.
13 Redefine window size by repositioning the window corners.
14 Move window toward top of file by one screen less two lines.
15 Move window toward end of file by one screen less two lines.
16 Move this line number to the first line of window.
17 Verify save of edited file; then close window.
18 Prompt for new name; then save the file under that name.
19 Enter a string to search for; then search forward.
20 Replace instances of one string with another.
21 Reserved for internal use.
22 Cancel the current prompt, menu, mode, or action.
23 Insert a specified ASCII character at the insertion point.
24 Redo the last edit on the current selection.
25 Undo the effect of the last edit. Undo again to restore the edit.
26 Select text with the mouse.
27 Search forward for the selected text.
28 Cycle next window to the top of the stack of windows.
29 Place this window at the bottom of the stack of windows.
30 Define a window; place the output of the selected system command in it.
31 No action.
32 Execute the system command interpreter. Type "EXIT" to return to POINT.
33 Load file into this window.
34 Move the selection cursor up one row.
35 Move the selection cursor down one row.
36 Move the selection cursor left one column.
37 Move the selection cursor right one column.
38 Hide window in the Window List menu.
39 Extend the selection to the current mouse position.
40 Undo multiple previous editing actions.
41 Reserved for internal use.
42 Reserved for internal use.
43 Reserved for internal use.
44 Reserved for internal use.
45 Execute one of nine commands depending on the mouse motion direction.
46 Execute one of nine commands depending on the mouse motion direction.
47 Save all edited files.
48 Save all edited files and exit POINT.
49 Verify discard of edits; then exit POINT.
50 User defined menu one (1).
51 User defined menu two (2).
52 User defined menu three (3).
53 Display a menu of available file windows.
54 Save the file.
55 Insert the contents of the scrap buffer in front of the insertion
point.
56 Move window back to the last file position viewed.
57 Copy the current selection to the scrap buffer.
58 Top the window containing the selection and position to show the
selection.
59 Toggle between insert and overtype entry modes.
60 User defined menu four (4).
61 Delete the current selection, preserving the contents of the scrap
buffer.
62 Exchange the current selection with the contents of the scrap buffer.
63 Display the Options menu for options changes in this editing session.
64 Enter the POINT Help system.
65 User defined menu five (5).
66 Search backward for the selected text.
67 User defined menu six (6).
68 Toggle POINT screen size between 43 and 25 lines of text (EGA, VGA
only).
69 Copy current selection to the mouse cursor position (on button
release).
70 Move current selection to the mouse cursor position (on button
release).
71 Reserved for internal use.
72 Save file and close the window.
73 Load the file specified by the current selection.
74 Move the cursor one word to the left.
75 Move the cursor one word to the right.
76 Begin or end recording keystrokes in the keyboard macro buffer.
77 Play back the keystrokes that are recorded in the keyboard macro buffer.
78 Move insertion point to the beginning of the file.
79 User defined menu seven (7).
80 User defined menu eight (8).
81 Change the case of the first character of the current selection.
82 Define a window, then open the file specified by the current selection.
83 Locate the matching bracket of the selected bracket.
84 Position the window at the line number specified by the current
selection.
85 Justify the current selection between the left border and the right
margin.
86 Toggle the read-only status of the file.
87 Cycle the color combinations of the window.
88 Exchange the two top windows, making the second window the top window.
89 Reserved for internal use.
90 Reserved for internal use.
91 Reserved for internal use.
92 Reserved for internal use.
93 User defined menu nine (9).
94 User defined menu ten (10).
95 User defined menu eleven (11).
96 User defined menu twelve (12).
97 User defined menu thirteen (13).
98 User defined menu fourteen (14).
99 User defined menu fifteen (15).
100 User defined menu sixteen (16).
101 Move window to a new location on the screen.
102 Anchor the keyboard selection at the current insertion point.
103 End keyboard selection mode.
104 Load file into a full-screen window.
105 Move the selection cursor to the beginning of the line.
106 Move the selection cursor to the end of the line.
107 Move the selection cursor to the top of the window.
108 Move the selection cursor to the bottom of the window.
109 Prompt for a printer device name; then print the file.
110 Display POINT Editor Version and Copyright information.
New "makeLas" Option
--------------------
POINT 2.01 supports an option to control the creation of the "PT.LAS"
file. Here are the possible values:
makeLas=0
Do not create a PT.LAS file.
makeLas=1
Create a PT.LAS file (this is the default).

View File

@ -0,0 +1,520 @@
Logitech Modula-2 Release 3.40 March, 1990
----------------------------------------------------------------------------
Logitech Modula-2 Release 3.40 READ.ME
======================================
This READ.ME file includes the installation instructions for Release
3.40; a list of the major changes between Release 3.40 and Release 3.03,
and additional new information about Release 3.40. It covers the Compiler
Pack, Toolkit, and the Development System. If you have purchased only
the Compiler Pack, you can ignore the references to the other packages
you did not purchase.
Installation of Logitech Modula-2 Release 3.40
==============================================
Logitech Modula-2 Release 3.40 requires a hard disk for installation.
The Compiler Pack requires approximately 2.4 megabytes of hard disk space
and the Toolkit requires approximately 1.7 megabytes. The Development
System consists of both the Compiler Pack and the Toolkit, so it's space
requirement is approximately 4.1 megabytes.
Both the Compiler Pack and the Toolkit are installed in a subdirectory
structure starting from a single subdirectory. The AUTOEXEC.BAT and
CONFIG.SYS files will be modified for the proper setup of the Modula-2
system.
The Compiler Pack and Toolkit installation disks contain special compressed
archives of the Logitech Modula-2 system. In order to properly install
Modula-2 Release 3.40, you must follow these instructions.
NOTE: The installation instructions presented here take precedence
over the installation instructions in the User's Manual and the
Toolkit Manual.
There are two installation methods provided for installing Logitech
Modula-2 Release 3.40: automatic and manual. The automatic installation
will prompt you for necessary information, and will automatically
update your AUTOEXEC.BAT and CONFIG.SYS files, if necessary. After it
completes the extraction of the files from the installation disks, the
installation of Modula-2 Release 3.40 will be complete. The manual
installation will require you to manually edit your CONFIG.SYS and
AUTOEXEC.BAT files, and use a batch file to extract the files from
the installation disks. Instructions for both methods follow.
NOTE: If you are replacing an earlier release of Logitech Modula-2 with
Release 3.40, you should remove all files and environment settings of the
previous release before installing the new release.
A. Automatic Installation
----------------------
1. To use the automatic installation, insert disk #1 of
the Compiler Pack or Toolkit in your diskette drive
and execute the provided INSTALL program. For example,
if you are installing the Compiler Pack or Development
System from drive A, you would insert the first Compiler
Pack disk in drive A and enter this command at the DOS
prompt:
A:INSTALL
If you are installing the Toolkit alone (if purchased
separately from the Development System), you would
perform the same step with the first Toolkit disk.
2. The install program will provide you with a series of
screens and prompts. An initial screen is displayed
that explains what the installation program is going
to do. After the help information is displayed,
press [Enter] to continue with the installation at
this prompt:
Continue with installation (YES/no) ?
If you do not want to continue, type
N [Enter]
3. You are then prompted to choose the particular Modula-2
3.40 package you wish to install. Enter number corresponding
to the package you are installing:
[1] Compiler Pack
[2] Toolkit
[3] Development System
[4] Quit installation
Choice?
(Note: If you wish to terminate the installation at this
point, select choice 4, "Quit installation".)
4. You will then be prompted for the source drive containing
the installation disk. Enter the drive letter at this
prompt:
Enter the letter of the diskette drive containing
the Logitech Modula-2 installation diskette
(default is A)
>
Press [Enter] to select the default drive A or type the
drive letter.
5. You will then be prompted for the directory where Logitech
Modula-2 will be installed. Enter the drive and path where
you want to install the Modula-2 system files:
Enter the full drive and path of the directory
where you want Logitech Modula-2 installed
(default is C:\M2)
>
Press [Enter] to accept the default C:\M2 or enter the drive
and directory. INSTALL will copy the Modula-2 system files
to this drive and directory.
6. You will then be prompted for the full pathname of your DOS
AUTOEXEC.BAT file. Enter the drive and path of your AUTOEXEC.BAT
file at this prompt:
Enter the full pathname of your DOS AUTOEXEC.BAT
file (default is C:\AUTOEXEC.BAT)
>
Press [Enter] to accept the default C:\AUTOEXEC.BAT or enter
the full pathname of the AUTOEXEC.BAT file.
7. You will then be prompted for the full pathname of your DOS
CONFIG.SYS file. Enter the drive and path of your CONFIG.SYS
file at this prompt:
Enter the full pathname of your DOS CONFIG.SYS file
(default is C:\CONFIG.SYS)
>
Press [Enter] to accept the default C:\CONFIG.SYS or enter
the full pathname of the CONFIG.SYS file.
8. The INSTALL program will then display the choices or entries
you have made. You can confirm these entries at this prompt:
Are these values correct (YES/no) ?
Press [Enter] to begin the installation of Logitech Modula-2
Release 3.40 on your system. If you enter no at this prompt,
install will restart at step 4 above.
Note: If the installation program determines that there
is inadequate disk space to install Modula-2 Release 3.40,
a warning is displayed. If this message is displayed,
press [Enter] to terminate the installation program.
9. As the AUTOEXEC.BAT and CONFIG.SYS files are updated,
INSTALL displays the installation's progress on the
screen. Backups of these files are saved before they
are modified (each with a .BAK extension).
INSTALL changes these files by
- adding the necessary directories to the PATH
statement
- adding necessary new environment settings for
the Modula-2 system (M2OBJ, M2MAK, etc.)
- ensuring that the environment space available
is at least 768 bytes
- ensuring that there are at least 20 file handles
available
10. You will then be prompted to insert the first disk. Press
[Enter] once the disk is inserted. INSTALL will then copy
the Modula-2 files from the installation disk to your
Logitech Modula-2 directory.
11. After the files from the first disk are copied, you will
then be prompted to insert the next disk. Perform step 10
above until all disks have been installed. After all of
the files have been copied, you will be returned to the
DOS prompt.
12. If you are currently using Microsoft C 5.1 and plan on
mixing Modula-2 code with C, add the following line to
the end of your AUTOEXEC.BAT file:
SET INCLUDE=%INCLUDE%;C:\M2\M2LIB\LIB
Note: replace "C:\M2" with the base installation directory
specified in step 5 above.
You should also read the README.DOC files in the EXAMPLES\C-MOD
and EXAMPLES\MOD-C subdirectories for details about mixing
Modula-2 and C code.
13. Reboot your system to activate the changes made to the
CONFIG.SYS and AUTOEXEC.BAT files.
B. Manual Installation
-------------------
1. You must begin by creating the Modula-2 directory on your
hard disk. For example, if you want to install Modula-2
in C:\M2, you would enter the following commands at the
DOS prompt:
C:
MD \M2
2. Next, you must change to the new M2 directory. Do this by
entering the following command:
CD \M2
3. You must then extract the files that form Logitech Modula-2
Release 3.40. If you wish to install either the Compiler Pack
or the Development System, insert the first Compiler Pack disk
in drive A. If you are installing only the Toolkit, insert the
Toolkit in drive A.
4. After the disk has been inserted, enter the following command:
A:M2UNPACK A:
The Modula-2 Release 3.40 files are extracted and copied to
the current directory, C:\M2. The argument "A:", which follows
M2UNPACK, specifies the drive containing the installation disk.
5. After the files from the first disk are copied, you will
then be prompted to insert the next disk. Insert each disk
until all the disks have been installed.
6. The Development System consists of both the Compiler Pack and
the Toolkit. If you are installing the Development System, you
should install the Toolkit after the Compiler Pack has been
installed. Insert the Toolkit disk in drive A, and perform
steps 4 and 5 until it has been installed.
7. You must now modify your DOS CONFIG.SYS file by adding and/or
modifying the "SHELL=" and "FILES=" statements.
The FILES= statement must be at least 20. Ensure that your
CONFIG.SYS contains the statement
FILES=20
The SHELL statement must be specified to increase the default
space available for environment strings. If you are using
DOS 3.1, add the line
SHELL=COMMAND.COM /P /E:48
to your CONFIG.SYS. If you are using DOS 3.2 or above, add
the line
SHELL=COMMAND.COM /P /E:768
to your CONFIG.SYS.
8. You must then modify your DOS AUTOEXEC.BAT file to include
necessary settings required by Modula-2 Release 3.40. The
settings here assume that Release 3.40 was installed in the
C:\M2 directory.
Modify the PATH statement to include the following
directories:
C:\M2\M2EXE;C:\M2\POINT
For example, if your PATH statement looked like this before
the modification:
SET PATH=C:\;C:\DOS;D:\BIN
it would look like this after the modification:
SET PATH=C:\M2\M2EXE;C:\M2\POINT;C:\;C:\DOS;D:\BIN
You must also append the following settings to the end of
your AUTOEXEC.BAT file:
SET M2SYM=C:\M2\M2LIB\SYM
SET M2LIB=C:\M2\M2LIB\LIB
SET M2OBJ=C:\M2\M2LIB\OBJ
SET M2REF=C:\M2\M2LIB\REF
SET M2DEF=C:\M2\M2LIB\DEF
SET M2MOD=C:\M2\M2LIB\MOD
SET M2MAP=C:\M2\M2LIB\MAP
SET M2TMP=C:\M2\M2TMP
SET M2OVL=C:\M2\M2EXE
SET M2MAK=C:\M2\M2EXE
SET M2LBR=C:\M2\M2EXE
(Note: if your system includes a RAM disk, you should set
the M2TMP variable to that drive).
9. If you are currently using Microsoft C 5.1 and plan on mixing
Modula-2 code with C, add the following line to the end of your
AUTOEXEC.BAT file:
SET INCLUDE=%INCLUDE%;C:\M2\M2LIB\LIB
You should also read the README.DOC files in the EXAMPLES\C-MOD
and EXAMPLES\MOD-C subdirectories for details about mixing
Modula-2 and C code.
10. After all of the necessary modifications have been made, reboot
your system to activate the changes.
Major Differences Between Release 3.40 and Release 3.03
=======================================================
Many enhancements have been made to the Logitech Modula-2 Development
System since Release 3.03. Some of these include:
- an enhanced compiler that provides 21-28% faster compilation,
and improved mixed-language support
- improved M2Make operation, including automatic support for the
generation of overlays
- enhanced debuggers, including new breakpoint and assembly windows,
and many new commands
- improved utilities, including greater speed of operation and
enhanced user interfaces
- a vastly improved POINT Editor, providing an improved user interface,
complete keyboard control, and better use of memory
- an improved M2L linker that provides complete support for the
Microsoft languages and mixed-language programming, and 10-20%
faster operation
Details of the enhancements and changes are provided in .DOC files for
each of the major programs. It is important to note as well that the
Cross-Reference function of M2Make has replaced the M2XRef utility in
the package; and the Formatter is no longer included. (All references
to these utilities in the Toolkit manual should be ignored.)
Here is a list of the .DOC files that contain the additional documentation
information about the differences between Release 3.03 and Release 3.40.
These files can be found in the M2DOC directory of the main Modula-2
installation directory.
CHANGES.DOC - general changes and information about
the compiler, linker, utilities, and
libraries
DEBUGGER.DOC - new information about the debuggers
POINT.DOC - new information about the POINT Editor
New Example Files
-----------------
Several new example files are provided with Release 3.40. These files
are in subdirectories of the EXAMPLES directory of the main Modula-2
installation directory. The examples included are mixed-langauge
programming with Microsoft C, an example of coroutines, the use of
the ANSI.SYS screen interface, and operations with files. Here is
a list of the example directories provided:
COROU - example of how to use coroutines
DIGCLOCK - digital clock using ANSI.SYS
FILEIO - example of performing basic file I/O
C-MOD - example of a C program that calls Logitech
Modula-2 procedures
MOD-C - example of a Logitech Modula-2 program
that calls C functions
Each directory contains a batch file, MAKE.BAT, that will compile,
link, and execute the example program. In addition, the mixed-language
examples contain README.DOC files giving additional information on how
to mix C with Modula-2.
Diskette Archive Contents
=========================
What follows is are lists of the contents of the archived files on
the distribution disks. Instructions for selectively extracting
different files from the archives follow these lists.
Compiler Pack
-------------
Disk #1: contents of M2340CP1.EXE
READ.ME
M2DOC\*.*
M2EXE\M2C.EXE
M2EXE\M2COMP.EXE
M2EXE\M2OVL3.OVL
M2EXE\M2OVL4.OVL
M2EXE\M2OVLINI.OVL
M2EXE\M2OVLLIS.OVL
M2EXE\M2OVLSYM.OVL
Disk #2: contents of M2340CP2.EXE
M2EXE\M2OVL1.OVL
M2EXE\PMD.EXE
M2EXE\DB.CFG
M2EXE\DB.HLP
M2EXE\DB.LBR
M2EXE\MDA.CFG
M2EXE\CGA.CFG
M2EXE\EGA.CFG
M2EXE\PTDEMO.MOD
POINT\*.*
EXAMPLES\C-MOD\*.*
EXAMPLES\MOD-C\*.*
EXAMPLES\FILEIO\*.*
Disk #3: contents of M2340CP3.EXE
M2LIB\DEF\*.*
M2LIB\SYM\*.*
M2LIB\LIB\*.*
M2LIB\OBJ\*.*
M2LIB\REF\RTSMAIN.REF
EXAMPLES\COROU\*.*
EXAMPLES\DIGCLOCK\*.*
Toolkit
-------
Disk #1: contents of M2340TK1.EXE
READ.ME
M2DOC\*.*
M2EXE\M2L.EXE
M2EXE\M2MAKE.EXE
M2EXE\LIBRARY.MAK
M2EXE\M2VERS.EXE
M2EXE\RTD.EXE
M2EXE\RTDINIT.OVL
M2EXE\RTDM2.OVL
M2EXE\RTDOVLAY.OVL
M2EXE\DB.CFG
M2EXE\DB.HLP
M2EXE\DB.LBR
M2EXE\MDA.CFG
M2EXE\CGA.CFG
M2EXE\EGA.CFG
Disk #2: contents of M2340TK2.EXE
M2EXE\M2CHECK.EXE
M2EXE\M2DECODE.EXE
M2LIB\ASM\*.*
M2LIB\MOD\*.*
M2LIB\REF\*.*
M2LIB\RTS\*.*
To selectively install files from these disks, perform the following
two steps:
1. Change to your Modula-2 3.40 base directory. If you
want to extract the files into a directory structure
starting at C:\M2, change to your C:\M2 directory.
For example:
C:
CD \M2
2. Execute the archive program that contains the files
you wish to extract, specifying the arguments "-d -o"
followed by the file specification(s) of the file(s)
you want to extract. For example, to extract all of
the M2LIB\MOD files from the Toolkit, you would insert
Toolkit Disk #2 in drive A, and enter the following
command:
A:M2340TK2 -d -o M2LIB\MOD\*.*
The directory structure contained in the archive will
automatically be created if it does not already exist.
----------------------------------------------------------------------
Copyright (C) 1989 Logitech, Inc.
Copyright (C) 1990 MultiScope, Inc. All Rights Reserved.

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,83 @@
Mouse functions
***************
CURSOR POSITION LEFT BUTTON MIDDLE BUTTON RIGHT BUTTON
CURSOR ON A WINDOW'S scroll up vertical scroll down
LEFT BORDER absolute position
CURSOR ON A WINDOW'S scroll left horizontal scroll right
BOTTOM BORDER absolute position
CURSOR ON A WINDOW'S move ------ ------
BOTTOM LEFT CORNER left/bottom border
CURSOR INSIDE simple click: call call
A WINDOW select window's window's
double click: manipulation specific
do probable action menu menu
PROMPT terminate escape escape
user entry prompt prompt
MENU execute the execute the execute the
highlighted highlighted highlighted
action action action
Scroll functions
****************
1 line up
|
|
+-------+-------+-------+
beginning | | | |
of text --- | HOME | ^ | PG UP |---- 1 page up
| | | |
+-------+-------+-------+
| | | |
1 column ------ | < | | > |---- 1 column
to the left | | | | to the right
+-------+-------+-------+
end of | | | |
text ------- | END | V | PG DN |---- 1 page down
| | | |
+-------+-------+-------+
|
|
1 line down
TAB : 1 page right SHIFT-TAB : 1 page left
Function keys
*************
F1 to call the help screen
ESC to leave the help screen
F10 to call the menu
cursor keys to select a command
CR or space to activate a command
ESC to leave the menu
In the menus, the following symbols are used:
the diamond sign = 'Alt' key,
the up arrow sign = 'Ctrl' key,
double quaver sign = double click.
Options
*******
PMD & RTD:
/q (default : /q-) Query
RTD:
/s (default : /s-) Small swap
/b (default : /b-) Big swap
/v (default : /v-) Virtual disk (drive d:)
/l (default : /l-) Large
/m (default : /m-) Mouse application and old driver
/g (default : /g-) Graphic application
It is advised to try first G-.
/d (default : /d+) Display handling


View File

@ -0,0 +1,62 @@
MODULE = ASCII s- p+
MODULE = BitBlockOps s- p+
MODULE = BitByteOps s- p+
MODULE = BitWordOps s- p+
MODULE = BlockOps s- p+
MODULE = Break s- p+
MODULE = Calendar s- p+
MODULE = CardinalIO s- p+
MODULE = Conversions s- p+
MODULE = Chronometer s- p+
MODULE = DateFormat s- p+
MODULE = DurationOps s- p+
MODULE = DebugPMD s- p+
MODULE = DebugTrace s- p+
MODULE = Decimals s- p+
MODULE = Delay s- p+
MODULE = Devices s- p+
MODULE = Directories s- p+
MODULE = DiskDirectory s- p+
MODULE = DiskFiles s- p+
MODULE = Display s- p+
MODULE = DOS3 s- p+
MODULE = DOS31 s- p+
MODULE = DosError s- p+
MODULE = DOSMemory s- p+
MODULE = DynMem s- p+
MODULE = ErrorCode s- p+
MODULE = Exec s- p+
MODULE = FileMessage s- p+
MODULE = FileNames s- p+
MODULE = FileSystem s- p+
MODULE = FloatingUtilities s- p+
MODULE = Graphics s- p+
MODULE = InOut s- p+
MODULE = Keyboard s- p+
MODULE = LoadPath s- p+
MODULE = LogiFile s- p+
MODULE = LongIO s- p+
MODULE = Lookup s- p+
MODULE = MathLib0 s- p+
MODULE = Mouse s- p+
MODULE = NumberConversion s- p+
MODULE = Options s- p+
MODULE = Processes s- p+
MODULE = Random s- p+
MODULE = RealConversions s- p+
MODULE = RealInOut s- p+
MODULE = RS232Code s- p+
MODULE = RS232Int s- p+
MODULE = RS232Polling s- p+
MODULE = RTSCoroutine s- p+
MODULE = RTSDevice s- p+
MODULE = RTSIntPROC s- p+
MODULE = RTSM87 s- p+
MODULE = RTSMain s- p+
MODULE = SimpleTerm s- p+
MODULE = Sounds s- p+
MODULE = Storage s- p+
MODULE = Strings s- p+
MODULE = Termbase s- p+
MODULE = Terminal s- p+
MODULE = TimeDate s- p+

Binary file not shown.

View File

@ -0,0 +1,63 @@
MODULE = ASCII
MODULE = BitBlockOps
MODULE = BitByteOps
MODULE = BitWordOps
MODULE = BlockOps
MODULE = Break
MODULE = Calendar
MODULE = CardinalIO
MODULE = Conversions
MODULE = Chronometer
MODULE = DateFormat
MODULE = DurationOps
MODULE = DebugPMD
MODULE = DebugTrace
MODULE = Decimals
MODULE = Delay
MODULE = Devices
MODULE = Directories
MODULE = DiskDirectory
MODULE = DiskFiles
MODULE = Display
MODULE = DOS3
MODULE = DOS31
MODULE = DosError
MODULE = DOSMemory
MODULE = DynMem
MODULE = ErrorCode
MODULE = Exec
MODULE = FileMessage
MODULE = FileNames
MODULE = FileSystem
MODULE = FloatingUtilities
MODULE = Graphics
MODULE = InOut
MODULE = Keyboard
MODULE = LoadPath
MODULE = LogiFile
MODULE = LongIO
MODULE = Lookup
MODULE = MathLib0
MODULE = Mouse
MODULE = NumberConversion
MODULE = Options
MODULE = Overlay
MODULE = Processes
MODULE = Random
MODULE = RealConversions
MODULE = RealInOut
MODULE = RS232Code
MODULE = RS232Int
MODULE = RS232Polling
MODULE = RTSCoroutine
MODULE = RTSDevice
MODULE = RTSIntPROC
MODULE = RTSM87
MODULE = RTSMain
MODULE = SimpleTerm
MODULE = Sounds
MODULE = Storage
MODULE = Strings
MODULE = Termbase
MODULE = Terminal
MODULE = TimeDate

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,18 @@
MODULE PtDemo;
FROM Terminal IMPORT WriteString, WriteLn;
PROCEDURE Hello (str : ARRAY OF CHAR);
VAR i : CARDINAL;
BEGIN
FOR i := 1 TO 10 DO
WriteString(str);
WriteLn;
END
END Hello
BEGIN
Hello("Hello Everybody"," !!!")
END PtDemo.


Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -0,0 +1,28 @@
echo off
rem installation for Modula-2 3.40 Compiler Pack
if exist %1m2340cp1.exe goto :disk1ok
:disk1
echo.
echo Insert Logitech Modula-2 Compiler Pack Disk #1 in drive %1 and
pause
if not exist %1m2340cp1.exe goto :disk1
:disk1ok
%1m2340cp1 -d -o
:disk2
echo.
echo Insert Logitech Modula-2 Compiler Pack Disk #2 in drive %1 and
pause
if not exist %1m2340cp2.exe goto :disk2
%1m2340cp2 -d -o
:disk3
echo.
echo Insert Logitech Modula-2 Compiler Pack Disk #3 in drive %1 and
pause
if not exist %1m2340cp3.exe goto :disk3
%1m2340cp3 -d -o
echo.

View File

@ -0,0 +1,464 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* BitBlockOps, operations on blocks *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
TITLE BitBlockOps
PUBLIC L__BlockAnd__BitBlockOps
PUBLIC L__BlockOr__BitBlockOps
PUBLIC L__BlockXor__BitBlockOps
PUBLIC L__BlockNot__BitBlockOps
PUBLIC L__BlockShr__BitBlockOps
PUBLIC L__BlockSar__BitBlockOps
PUBLIC L__BlockShl__BitBlockOps
PUBLIC L__BlockRor__BitBlockOps
PUBLIC L__BlockRol__BitBlockOps
PUBLIC KEY__10aug87_2030_OF_BitBlockOps
PUBLIC $OK__31jul87_1000_OF_BitBlockOps
KEY__10aug87_2030_OF_BitBlockOps EQU 0
PUBLIC $INIT__BitBlockOps
PUBLIC $BM__BitBlockOps, $EM__BitBlockOps
; PUBLIC $BD__BitBlockOps, $ED__BitBlockOps
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__31jul87_1000_OF_BitBlockOps DW 0AEFFH,0258H,0
MODULE_TABLE_DATA ENDS
IFDEF MEDIUM
DGROUP GROUP MODULE_TABLE_DATA
ENDIF
BitBlockOps_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:BitBlockOps_TEXT
ASSUME DS:NOTHING
$BM__BitBlockOps:
;-----------------------------------------------------------
L__BlockAnd__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (destination, source : ADDRESS;
; blocksize : CARDINAL);
blocksize = 6
source = blocksize + 2
destination = source + 4
PUSH BP
MOV BP, SP
MOV CX, [BP + blocksize]
JCXZ ANDEPILOG
IFDEF MEDIUM
MOV BX, DS
ENDIF
CLD
LDS SI, DWORD PTR [BP + source]
LES DI, DWORD PTR [BP + destination]
ANDAGAIN: LODSB ; MOV AL,DS:[SI] INC SI
AND BYTE PTR ES:[DI], AL
INC DI
LOOP ANDAGAIN
IFDEF MEDIUM
MOV DS, BX
ENDIF
ANDEPILOG: POP BP
RET 10
L__BlockAnd__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockOr__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (destination, source : ADDRESS;
; blocksize : CARDINAL);
blocksize = 6
source = blocksize + 2
destination = source + 4
PUSH BP
MOV BP, SP
CLD
MOV CX, [BP + blocksize]
JCXZ OREPILOG
IFDEF MEDIUM
MOV BX, DS
ENDIF
LDS SI, DWORD PTR [BP + source]
LES DI, DWORD PTR [BP + destination]
ORAGAIN: LODSB
OR BYTE PTR ES:[DI], AL
INC DI
LOOP ORAGAIN
IFDEF MEDIUM
MOV DS, BX
ENDIF
OREPILOG: POP BP
RET 10
L__BlockOr__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockXor__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (destination, source : ADDRESS;
; blocksize : CARDINAL);
blocksize = 6
source = blocksize + 2
destination = source + 4
PUSH BP
MOV BP, SP
IFDEF MEDIUM
MOV BX, DS
ENDIF
MOV CX, [BP + blocksize]
CLD
LDS SI, DWORD PTR [BP + source]
JCXZ XOREPILOG
LES DI, DWORD PTR [BP + destination]
XORAGAIN: LODSB
XOR BYTE PTR ES:[DI], AL
INC DI
LOOP XORAGAIN
XOREPILOG:
IFDEF MEDIUM
MOV DS, BX
ENDIF
POP BP
RET 10
L__BlockXor__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockNot__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (block : ADDRESS;
; blocksize : CARDINAL);
blocksize = 6
block = blocksize + 2
PUSH BP
MOV BP, SP
MOV CX, [BP + blocksize]
JCXZ NOTEPILOG
LES DI, DWORD PTR [BP + block]
NOTAGAIN: NOT BYTE PTR ES:[DI]
INC DI
LOOP NOTAGAIN
NOTEPILOG: POP BP
RET 6
L__BlockNot__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockShr__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (block : ADDRESS;
; blocksize : CARDINAL;
; count : CARDINAL);
count = 6
blocksize = count + 2
block = blocksize + 2
PUSH BP
MOV BP, SP
LDS SI, DWORD PTR [BP + block]
MOV BX, [BP + blocksize]
XOR AH, AH ; fill with 0's from the left
JMP RIGHT ; generic right shift
L__BlockShr__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockSar__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (block : ADDRESS;
; blocksize : CARDINAL;
; count : CARDINAL);
count = 6
blocksize = count + 2
block = blocksize + 2
PUSH BP
MOV BP, SP
LDS SI, DWORD PTR [BP + block]
MOV BX, [BP + blocksize]
MOV AL, BYTE PTR [BX+SI-1] ; get high byte
CBW ; sign extend
; common right-shift entry point
; BX = blocksize
; DS:SI = block ptr (points to low byte)
; AH = fill byte (bits used to fill on left)
RIGHT:
MOV DH, AH ; save fill-byte for later
CLD ; clear direction flag
MOV CX, [BP + count] ; shift count
AND CX, 07H ; count MOD 8
JZ RGHTEVEN ; shift is by an even number of bytes
ADD SI, BX ; point past last byte
RIGHT1:
DEC SI ; point to byte[n]
MOV AL, BYTE PTR [SI] ; get byte[n]
MOV DL, AL ; save it, needed for byte[n-1]
SHR AX, CL ; shr, including bits from byte[n+1]
MOV BYTE PTR [SI], AL ; update byte[n]
MOV AH, DL ; put old value in AX for next iter
DEC BX ; was that the last one?
JNZ RIGHT1 ; nope
; note: DS:SI = block again
MOV BX, [BP + blocksize]
; shift bytes right by (count DIV 8), extend with DH
RGHTEVEN: MOV AX, [BP + count] ; get shift count
SHR AX, 1
SHR AX, 1
SHR AX, 1 ; compute count DIV 8
JZ RIGHTX ; zip: no byte shuffle needed
LES DI, DWORD PTR [BP + block]
MOV CX, BX ; blocksize again
CMP CX, AX ; (count DIV 8) >= blocksize?
JBE RGHTFILL ; just fill with sign
SUB CX, AX ; blocksize - (count DIV 8)
ADD SI, AX ; first byte to keep
REP MOVSB ; move CX bytes at DS:[SI] to ES:[DI]
MOV CX, AX ; and fill the balance with sign
RGHTFILL: MOV AL, DH ; use that saved sign-byte
REP STOSB ; fill CX bytes at ES:[DI] with sign
RIGHTX:
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 8
L__BlockSar__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockShl__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (block : ADDRESS;
; blocksize : CARDINAL;
; count : CARDINAL);
count = 6
blocksize = count + 2
block = blocksize + 2
PUSH BP
MOV BP, SP
CLD
LDS SI, DWORD PTR [BP + block] ; point to low byte
MOV BX, [BP + blocksize]
MOV CX, [BP + count]
AND CL, 07H
JZ SHL8
; shift bytes left by count MOD 8
XOR AL, AL ; fill 0's from right
SHLOOP1: MOV AH, BYTE PTR [SI] ; get byte n
MOV DH, AH ; save it for next iter
ROL AX, CL ; shift byte n, n-1
MOV AL, DH
MOV BYTE PTR [SI], AH ; update byte n
INC SI
DEC BX
JNZ SHLOOP1
MOV BX, WORD PTR [BP + blocksize]
; Block move of count DIV 8 bytes, and clear of high bytes
SHL8: MOV AX, [BP + count]
SHR AX, 1
SHR AX, 1
SHR AX, 1
JZ SHLEPILOG
STD
LES SI, DWORD PTR [BP + block] ; load ES, reset SI
LEA DI, BYTE PTR [SI + BX - 1] ; ES:DI points to last byte
MOV CX, BX
CMP CX, AX ; blocksize <= (count DIV 8)?
JBE SHLZERO ; yes, fill the whole thing
SUB CX, AX ; CX = bytes to keep
ADD SI, CX ;
DEC SI ; leftmost byte to keep
REP MOVSB ; shuffle bytes left (up)
MOV CX, AX
SHLZERO: XOR AL, AL
REP STOSB ; zero the rest (low bytes)
SHLEPILOG: CLD
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 8
L__BlockShl__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockRor__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (block : ADDRESS;
; blocksize : CARDINAL;
; count : CARDINAL);
count = 6
blocksize = count + 2
block = blocksize + 2
PUSH BP
MOV BP, SP
CLD
MOV BX, [BP + blocksize]
LDS SI, DWORD PTR [BP + block] ; point to low byte
MOV CX, [BP + count]
AND CX, 07H
JZ ROR8 ; (count MOD 8) = 0
; working high to low, rotate the block in-place by (count MOD 8) bits
; taking care to wrap the low bits of the low byte into the high byte
MOV AH, BYTE PTR [SI] ; save low byte
LEA SI, BYTE PTR [SI + BX - 1] ; point to last (high) byte
ROR1:
MOV AL, BYTE PTR [SI] ; get byte n
MOV DL, AL ; save to do byte n-1
ROR AX, CL ; shift right with byte n+1
MOV BYTE PTR [SI], AL ; store new byte n
MOV AH, DL ; recover old byte n
DEC SI ; point to byte n-1
DEC BX ; more bytes to do?
JNZ ROR1 ; yes: repeat blocksize times
MOV BX, [BP + blocksize] ; restore BX = blocksize
ROR8: MOV DX, [BP + count]
SHR DX, 1
SHR DX, 1
SHR DX, 1
JZ ROREPILOG ; (count DIV 8) = 0
; ugh: shuffle right by 1 byte, repeat DX = (count DIV 8) times
LES DI, DWORD PTR [BP + block] ; ES:DI points to low byte
ROR3:
MOV SI, DI ; ditto DS:SI (DS loaded above)
LEA CX, BYTE PTR [BX - 1] ; CX := blocksize - 1
LODSB ; save low byte in AL
REP MOVSB ; shuffle other bytes down
STOSB ; put old low byte into high
SUB DI, BX ; restore ES:DI to low byte
DEC DX
JNZ ROR3 ; repeat (count DIV 8) times
ROREPILOG:
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 8
L__BlockRor__BitBlockOps ENDP
;-----------------------------------------------------------
L__BlockRol__BitBlockOps PROC FAR
;-----------------------------------------------------------
; in : (block : ADDRESS;
; blocksize : CARDINAL;
; count : CARDINAL);
count = 6
blocksize = count + 2
block = blocksize + 2
PUSH BP
MOV BP, SP
MOV BX, [BP + blocksize]
LDS SI, DWORD PTR [BP + block]
MOV CX, [BP + count]
AND CX, 07H
JZ ROL8 ; (count MOD 8) = 0
MOV AH, BYTE PTR [SI + BX - 1] ; save high byte
ROL1:
MOV AL, BYTE PTR [SI] ; get byte n
MOV DL, AL ; save for n+1
ROL AX, CL
MOV BYTE PTR [SI], AL ; update byte n
MOV AH, DL
INC SI
DEC BX
JNZ ROL1
MOV BX, [BP + blocksize]
ROL8: MOV DX, [BP + count]
SHR DX, 1
SHR DX, 1
SHR DX, 1
JZ ROLX
STD
LES DI, DWORD PTR [BP + block] ; first byte
LEA DI, BYTE PTR [DI + BX - 1] ; ES:DI points to last byte
ROL3:
MOV SI, DI ; DS:SI ditto, (DS set above)
LEA CX, BYTE PTR [BX-1] ; CX = blocksize - 1
LODSB ; save high byte (AL)
REP MOVSB ; shuffle up by one byte!!
STOSB ; stuff old high into low
ADD DI, BX ; reset ES:DI to last byte
DEC DX
JNZ ROL3 ; repeat (count DIV 8) times
ROLX: CLD
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 8
L__BlockRol__BitBlockOps ENDP
$INIT__BitBlockOps PROC FAR
RET
$INIT__BitBlockOps ENDP
$EM__BitBlockOps:
BitBlockOps_TEXT ENDS
;BitBlockOps_DATA SEGMENT WORD PUBLIC 'FAR_BSS'
; ASSUME CS : BitBlockOps_TEXT
;$BD__BitBlockOps LABEL FAR
;
;$ED__BitBlockOps LABEL FAR
;BitBlockOps_DATA ENDS
END

View File

@ -0,0 +1,357 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* BitByteOps, bitwise operations on bytes *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
TITLE BitByteOps
PUBLIC L__GetBits__BitByteOps
PUBLIC L__SetBits__BitByteOps
PUBLIC L__ByteAnd__BitByteOps
PUBLIC L__ByteOr__BitByteOps
PUBLIC L__ByteXor__BitByteOps
PUBLIC L__ByteNot__BitByteOps
PUBLIC L__ByteShr__BitByteOps
PUBLIC L__ByteSar__BitByteOps
PUBLIC L__ByteShl__BitByteOps
PUBLIC L__ByteRor__BitByteOps
PUBLIC L__ByteRol__BitByteOps
PUBLIC L__HighNibble__BitByteOps
PUBLIC L__LowNibble__BitByteOps
PUBLIC L__Swap__BitByteOps
PUBLIC KEY__10aug87_2030_OF_BitByteOps
PUBLIC $OK__31jul87_1100_OF_BitByteOps
KEY__10aug87_2030_OF_BitByteOps EQU 0
PUBLIC $INIT__BitByteOps
PUBLIC $BM__BitByteOps, $EM__BitByteOps
; PUBLIC $BD__BitByteOps, $ED__BitByteOps
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__31jul87_1100_OF_BitByteOps DW 0AEFFH,0294H,0
MODULE_TABLE_DATA ENDS
BitByteOps_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:BitByteOps_TEXT
ASSUME DS:NOTHING
$BM__BitByteOps:
;-----------------------------------------------------------
L__GetBits__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (source: BYTE;
; firstBit, lastBit : CARDINAL): BYTE;
lastBit = 6
firstBit = lastBit + 2
source = firstBit + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + source]
MOV CL, 15
SUB CL, [BP + lastBit]
SHL AX, CL
ADD CL, [BP + firstBit]
SHR AX, CL
XOR AH, AH
POP BP
RET 6
L__GetBits__BitByteOps ENDP
;-----------------------------------------------------------
L__SetBits__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (VAR byte : BYTE;
; firstBit, lastBit: CARDINAL;
; value : BYTE)
value = 6
lastBit = value + 2
firstBit = lastBit + 2
_byte = firstBit + 2
PUSH BP
MOV BP, SP
MOV BX, [BP + value]
MOV AX, 0FFFFH
MOV CL, [BP + firstBit]
SHR AX, CL
SHL AX, CL ; clip mask on right
SHL BX, CL ; position value
MOV CL, 15
SUB CL, [BP + lastBit]
SHL AX, CL
SHR AX, CL ; clip mask on left
AND BX, AX ; mask new value
NOT AX
LES DI, DWORD PTR [BP + _byte]
AND AL, BYTE PTR ES:[DI] ; get byte, mask out affected bits
OR AL, BL ; plug in new value
MOV BYTE PTR ES:[DI], AL
POP BP
RET 10
L__SetBits__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteAnd__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (left, right : BYTE): BYTE;
right = 6
left = right + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + left]
AND AX, [BP + right]
XOR AH, AH
POP BP
RET 4
L__ByteAnd__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteOr__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (left, right : BYTE): BYTE;
right = 6
left = right + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + left]
OR AX, [BP + right]
XOR AH, AH
POP BP
RET 4
L__ByteOr__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteXor__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (left, right : BYTE): BYTE;
right = 6
left = right + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + left]
XOR AX, [BP + right]
XOR AH, AH
POP BP
RET 4
L__ByteXor__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteNot__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte : BYTE): BYTE;
_byte = 6
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
NOT AX
XOR AH, AH
POP BP
RET 2
L__ByteNot__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteShr__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte : BYTE;
; count : CARDINAL): BYTE;
count = 6
_byte = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
MOV CX, [BP + count]
XOR AH, AH
SHR AL, CL
POP BP
RET 4
L__ByteShr__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteSar__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte : BYTE;
; count : CARDINAL): BYTE;
count = 6
_byte = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
MOV CX, [BP + count]
XOR AH, AH
SAR AL, CL
POP BP
RET 4
L__ByteSar__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteShl__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte : BYTE;
; count : CARDINAL): BYTE;
count = 6
_byte = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
MOV CX, [BP + count]
XOR AH, AH
SHL AL, CL
POP BP
RET 4
L__ByteShl__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteRor__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte : BYTE;
; count : CARDINAL): BYTE;
count = 6
_byte = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
MOV CX, [BP + count]
XOR AH, AH
ROR AL, CL
POP BP
RET 4
L__ByteRor__BitByteOps ENDP
;-----------------------------------------------------------
L__ByteRol__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte : BYTE;
; count : CARDINAL): BYTE;
count = 6
_byte = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
MOV CX, [BP + count]
XOR AH, AH
ROL AL, CL
POP BP
RET 4
L__ByteRol__BitByteOps ENDP
;-----------------------------------------------------------
L__HighNibble__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte: BYTE): CARDINAL;
_byte = 6
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
XOR AH, AH
MOV CL, 4
SHR AL, CL
POP BP
RET 2
L__HighNibble__BitByteOps ENDP
;-----------------------------------------------------------
L__LowNibble__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (byte: BYTE): CARDINAL;
_byte = 6
PUSH BP
MOV BP, SP
MOV AX, [BP + _byte]
XOR AH, AH
AND AL, 0FH
POP BP
RET 2
L__LowNibble__BitByteOps ENDP
;-----------------------------------------------------------
L__Swap__BitByteOps PROC FAR
;-----------------------------------------------------------
; in : (VAR byte: BYTE)
_byte = 6
PUSH BP
MOV BP, SP
LES DI, DWORD PTR [BP + _byte]
MOV CL, 4
MOV AL, BYTE PTR ES:[DI]
ROR AL, CL
MOV BYTE PTR ES:[DI], AL
POP BP
RET 4
L__Swap__BitByteOps ENDP
$INIT__BitByteOps PROC FAR
RET
$INIT__BitByteOps ENDP
$EM__BitByteOps:
BitByteOps_TEXT ENDS
;BitByteOps_DATA SEGMENT BYTE PUBLIC 'FAR_BSS'
; ASSUME CS : BitByteOps_TEXT
;$BD__BitByteOps LABEL FAR
;
;$ED__BitByteOps LABEL FAR
;BitByteOps_DATA ENDS
END

View File

@ -0,0 +1,354 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* BitWordOps, bitwise operations on words *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
TITLE BitWordOps
PUBLIC L__GetBits__BitWordOps
PUBLIC L__SetBits__BitWordOps
PUBLIC L__WordAnd__BitWordOps
PUBLIC L__WordOr__BitWordOps
PUBLIC L__WordXor__BitWordOps
PUBLIC L__WordNot__BitWordOps
PUBLIC L__WordShr__BitWordOps
PUBLIC L__WordSar__BitWordOps
PUBLIC L__WordShl__BitWordOps
PUBLIC L__WordRor__BitWordOps
PUBLIC L__WordRol__BitWordOps
PUBLIC L__HighByte__BitWordOps
PUBLIC L__LowByte__BitWordOps
PUBLIC L__Swap__BitWordOps
PUBLIC KEY__10aug87_2030_OF_BitWordOps
PUBLIC $OK__31jul87_1200_OF_BitWordOps
KEY__10aug87_2030_OF_BitWordOps EQU 0
PUBLIC $INIT__BitWordOps
PUBLIC $BM__BitWordOps, $EM__BitWordOps
; PUBLIC $BD__BitWordOps, $ED__BitWordOps
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__31jul87_1200_OF_BitWordOps DW 0AEFFH,02D0H,0
MODULE_TABLE_DATA ENDS
BitWordOps_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:BitWordOps_TEXT
ASSUME DS:NOTHING
$BM__BitWordOps:
;-----------------------------------------------------------
L__GetBits__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (source, firstBit, lastBit : WORD): WORD;
lastBit = 6
firstBit = lastBit + 2
source = firstBit + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + source]
MOV CL, 15
SUB CL, [BP + lastBit]
SHL AX, CL
ADD CL, [BP + firstBit]
SHR AX, CL
POP BP
RET 6
L__GetBits__BitWordOps ENDP
;-----------------------------------------------------------
L__SetBits__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (VAR word : WORD;
; firstBit, lastBit: CARDINAL;
; value : WORD)
value = 6
lastBit = value + 2
firstBit = lastBit + 2
_word = firstBit + 2
PUSH BP
MOV BP, SP
MOV BX, [BP + value]
MOV AX, 65535
MOV CL, 15
SUB CL, [BP + lastBit]
SHL AX, CL
ADD CL, [BP + firstBit]
SHR AX, CL
MOV CL, [BP + firstBit]
SHL BX, CL
SHL AX, CL
AND BX, AX
NOT AX
LES DI, DWORD PTR [BP + _word]
MOV CX, WORD PTR ES:[DI]
AND CX, AX
OR CX, BX
MOV WORD PTR ES:[DI], CX
POP BP
RET 10
L__SetBits__BitWordOps ENDP
;-----------------------------------------------------------
L__WordAnd__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (left, right : WORD): WORD;
right = 6
left = right + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + left]
MOV BX, [BP + right]
AND AX, BX
POP BP
RET 4
L__WordAnd__BitWordOps ENDP
;-----------------------------------------------------------
L__WordOr__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (left, right : WORD): WORD;
right = 6
left = right + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + left]
MOV BX, [BP + right]
OR AX, BX
POP BP
RET 4
L__WordOr__BitWordOps ENDP
;-----------------------------------------------------------
L__WordXor__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (left, right : WORD): WORD;
right = 6
left = right + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + left]
MOV BX, [BP + right]
XOR AX, BX
POP BP
RET 4
L__WordXor__BitWordOps ENDP
;-----------------------------------------------------------
L__WordNot__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word : WORD): WORD;
_word= 6
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
NOT AX
POP BP
RET 2
L__WordNot__BitWordOps ENDP
;-----------------------------------------------------------
L__WordShr__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word : CARDINAL;
; count : WORD): WORD;
count = 6
_word = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
MOV CX, [BP + count]
SHR AX, CL
POP BP
RET 4
L__WordShr__BitWordOps ENDP
;-----------------------------------------------------------
L__WordSar__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word : CARDINAL;
; count : WORD): WORD;
count = 6
_word = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
MOV CX, [BP + count]
SAR AX, CL
POP BP
RET 4
L__WordSar__BitWordOps ENDP
;-----------------------------------------------------------
L__WordShl__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word : CARDINAL;
; count : WORD): WORD;
count = 6
_word = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
MOV CX, [BP + count]
SHL AX, CL
POP BP
RET 4
L__WordShl__BitWordOps ENDP
;-----------------------------------------------------------
L__WordRor__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word : CARDINAL;
; count : WORD): WORD;
count = 6
_word = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
MOV CX, [BP + count]
ROR AX, CL
POP BP
RET 4
L__WordRor__BitWordOps ENDP
;-----------------------------------------------------------
L__WordRol__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word : CARDINAL;
; count : WORD): WORD;
count = 6
_word = count + 2
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
MOV CX, [BP + count]
ROL AX, CL
POP BP
RET 4
L__WordRol__BitWordOps ENDP
;-----------------------------------------------------------
L__HighByte__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word: WORD): CARDINAL;
_word = 6
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
MOV CL, 8
SHR AX, CL
POP BP
RET 2
L__HighByte__BitWordOps ENDP
;-----------------------------------------------------------
L__LowByte__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (word: WORD): CARDINAL;
_word = 6
PUSH BP
MOV BP, SP
MOV AX, [BP + _word]
XOR AH, AH
POP BP
RET 2
L__LowByte__BitWordOps ENDP
;-----------------------------------------------------------
L__Swap__BitWordOps PROC FAR
;-----------------------------------------------------------
; in : (VAR word: WORD)
_word = 6
PUSH BP
MOV BP, SP
LES DI, DWORD PTR [BP+_word]
MOV BX, WORD PTR ES:[DI]
XCHG BH, BL
MOV WORD PTR ES:[DI], BX
POP BP
RET 4
L__Swap__BitWordOps ENDP
$INIT__BitWordOps PROC FAR
RET
$INIT__BitWordOps ENDP
$EM__BitWordOps:
BitWordOps_TEXT ENDS
;BitWordOps_DATA SEGMENT WORD PUBLIC 'FAR_BSS'
; ASSUME CS : BitWordOps_TEXT
;$BD__BitWordOps LABEL FAR
;
;$ED__BitWordOps LABEL FAR
;BitWordOps_DATA ENDS
END


View File

@ -0,0 +1,342 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* BlockOps, operations on blocks *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
TITLE BlockOps
PUBLIC L__BlockMoveBackward__BlockOps
PUBLIC L__BlockMoveForward__BlockOps
PUBLIC L__BlockMove__BlockOps
PUBLIC L__BlockClear__BlockOps
PUBLIC L__BlockSet__BlockOps
PUBLIC L__BlockEqual__BlockOps
PUBLIC L__BlockPosition__BlockOps
PUBLIC KEY__10aug87_2030_OF_BlockOps
PUBLIC $OK__31jul87_1300_OF_BlockOps
KEY__10aug87_2030_OF_BlockOps EQU 0
PUBLIC $INIT__BlockOps
PUBLIC $BM__BlockOps, $EM__BlockOps
; PUBLIC $BD__BlockOps, $ED__BlockOps
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__31jul87_1300_OF_BlockOps DW 0AEFFH,030CH,0
MODULE_TABLE_DATA ENDS
IFDEF MEDIUM
DGROUP GROUP MODULE_TABLE_DATA;
ENDIF
BlockOps_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:BlockOps_TEXT
ASSUME DS:NOTHING
$BM__BlockOps:
;-----------------------------------------------------------
L__BlockMoveForward__BlockOps PROC FAR
;-----------------------------------------------------------
; in : destination, source : ADDRESS;
; size : CARDINAL;
_size = 6
source = _size + 2
destination = source + 4
PUSH BP
MOV BP, SP
IFDEF MEDIUM
MOV BX, DS
ENDIF
CLD
LDS SI, DWORD PTR [BP + source]
LES DI, DWORD PTR [BP + destination]
MOV CX, [BP + _size]
SHR CX, 1
REP MOVSW ; move words from DS:SI to ES:DI
ADC CX, 0 ; if byte count was odd..
REP MOVSB ; move the odd byte
IFDEF MEDIUM
MOV DS, BX
ENDIF
POP BP
RET 10
L__BlockMoveForward__BlockOps ENDP
;-----------------------------------------------------------
L__BlockMoveBackward__BlockOps PROC FAR
;-----------------------------------------------------------
; in : destination, source : ADDRESS;
; size : CARDINAL;
_size = 6
source = _size + 2
destination = source + 4
PUSH BP
MOV BP, SP
IFDEF MEDIUM
MOV BX, DS
ENDIF
LDS SI, DWORD PTR [BP + source]
LES DI, DWORD PTR [BP + destination]
MOV CX, [BP + _size]
MoveUp: STD
DEC CX
ADD SI, CX ; point to high source byte
ADD DI, CX ; point to high dest byte
INC CX ; get back byte count
SHR CX, 1 ; CX = words to move
JNC Muppet ; even number of words
MOVSB ; move highest (odd) byte
Muppet:
DEC SI ; point to high source word
DEC DI ; point to high dest word
REP MOVSW ; move rest of block by words
CLD
IFDEF MEDIUM
MOV DS, BX
ENDIF
POP BP
RET 10
L__BlockMoveBackward__BlockOps ENDP
;-----------------------------------------------------------
L__BlockMove__BlockOps PROC FAR
;-----------------------------------------------------------
; in : destination, source : ADDRESS;
; size : CARDINAL;
_size = 6
source = _size + 2
destination = source + 4
PUSH BP
MOV BP, SP
CLD
MOV CL, 4
LDS SI, DWORD PTR [BP + source]
; compute normalized source address in AX:BX (BX <= 16)
MOV BX, SI
AND BX, 0FH ; offset MOD 16 -> BX
SHR SI, CL
MOV AX, DS
ADD AX, SI ; seg + offset DIV 16 -> AX
; compute normalized destination in CX:DX
LES DI, DWORD PTR [BP + destination]
MOV DX, DI
AND DX, 0FH ; offset MOD 16 -> DX
SHR DI, CL
MOV CX, ES
ADD CX, DI ; seg + offset DIV 16 -> CX
LDS SI, DWORD PTR [BP + source]
LES DI, DWORD PTR [BP + destination]
CMP CX, AX ; destination follows source?
MOV CX, [BP + _size]
JNE WARD
CMP DX, BX ; para are equal, chk offsets
JE MVEPILOG ; dst = src, no action
WARD: JA MoveUp ; dst > src
SHR CX, 1
REP MOVSW
ADC CX, 0
REP MOVSB ; move last byte, if any
MVEPILOG:
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 10
L__BlockMove__BlockOps ENDP
;-----------------------------------------------------------
L__BlockClear__BlockOps PROC FAR
;-----------------------------------------------------------
; in : source : ADDRESS;
; size : CARDINAL;
_size = 6
source = _size + 2
PUSH BP
MOV BP, SP
LES DI, DWORD PTR [BP + source]
CLD
XOR AX, AX
MOV CX, [BP + _size]
SHR CX, 1
REP STOSW
ADC CX, 0
REP STOSB
POP BP
RET 6
L__BlockClear__BlockOps ENDP
;-----------------------------------------------------------
L__BlockSet__BlockOps PROC FAR
;-----------------------------------------------------------
; in : block : ADDRESS;
; blockSize : CARDINAL;
; pattern : ADDRESS;
; patternSize : CARDINAL;
patternSize = 6
pattern = patternSize + 2
blockSize = pattern + 4
block = blockSize + 2
PUSH BP
MOV BP, SP
CLD
MOV BX, [BP + blockSize]
LES DI, DWORD PTR [BP + block]
LOP: MOV CX, [BP + patternSize]
LDS SI, DWORD PTR [BP + pattern]
CMP CX, BX
JAE EXIT ; 1 or fewer patterns left to do
SUB BX, CX ; reduce total byte count by 1 pattern
REP MOVSB ; copy pattern once
JMP LOP
EXIT: MOV CX, BX ; just do remaining part of block
REP MOVSB
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 12
L__BlockSet__BlockOps ENDP
;-----------------------------------------------------------
L__BlockEqual__BlockOps PROC FAR
;-----------------------------------------------------------
; in : left, right : ADDRESS;
; count : CARDINAL;
; out : BOOLEAN;
count = 6
right = count + 2
left = right + 4
PUSH BP
MOV BP, SP
IFDEF MEDIUM
MOV BX, DS
ENDIF
CLD
MOV CX, [BP + count]
XOR AX, AX ; assume value is FALSE
LDS SI, DWORD PTR [BP + left]
LES DI, DWORD PTR [BP + right]
SHR CX, 1 ; compute word count
JNC EQEVN ; even number of words
CMPSB ; odd - compare the odd bytes
JNE EQEPILOG ; well well well, that was easy
EQEVN: REPE CMPSW ; compare by words (CX = 0 falls thru)
JNE EQEPILOG ; some word differed
EQT: MOV AX, 1 ; return TRUE
EQEPILOG:
IFDEF MEDIUM
MOV DS, BX
ENDIF
POP BP
RET 10
L__BlockEqual__BlockOps ENDP
;-----------------------------------------------------------
L__BlockPosition__BlockOps PROC FAR
;-----------------------------------------------------------
; in : block : ADDRESS;
; blockSize : CARDINAL;
; pattern : ADDRESS;
; patternSize : CARDINAL;
; out : CARDINAL;
patternSize = 6
pattern = patternSize + 2
blockSize = pattern + 4
block = blockSize + 2
PUSH BP
MOV BP, SP
CLD
XOR AX, AX
MOV DX, [BP + patternSize]
TEST DX, DX
JZ POSEPILOG ; trivial match (null pattern)
MOV BX, [BP + blockSize]
SUB BX, DX ; BX = last possible position
JB NOTFOUND ; none
WHILE:
MOV CX, DX ; CX = patternSize
LDS SI, DWORD PTR [BP + pattern]
LES DI, DWORD PTR [BP + block]
ADD DI, AX ; offset to current position
REPE CMPSB
JE POSEPILOG ; match
INC AX ; try at next position
CMP AX, BX
JBE WHILE
NOTFOUND: MOV AX, 65535
POSEPILOG:
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 12
L__BlockPosition__BlockOps ENDP
$INIT__BlockOps PROC FAR
RET
$INIT__BlockOps ENDP
$EM__BlockOps:
BlockOps_TEXT ENDS
;BlockOps_DATA SEGMENT WORD PUBLIC 'FAR_BSS'
; ASSUME CS : BlockOps_TEXT
;$BD__BlockOps LABEL FAR
;
;$ED__BlockOps LABEL FAR
;BlockOps_DATA ENDS
END

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,537 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* DynMem : dynamic memory management in fixed block *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
TITLE DynMem
IFDEF OS2
POPFF MACRO
LOCAL A
JMP $+3
A LABEL NEAR
IRET
PUSH CS
CALL A
ENDM
ENDIF
PUBLIC L__Alloc__DynMem
PUBLIC L__DeAlloc__DynMem
PUBLIC L__Avail__DynMem
PUBLIC L__InstallDynMem__DynMem
PUBLIC $OK__16jun87_1952_OF_DynMem
PUBLIC KEY__10aug87_2031_OF_DynMem
KEY__10aug87_2031_OF_DynMem EQU 0
PUBLIC $INIT__DynMem
PUBLIC $BM__DynMem, $EM__DynMem
;====== FROM RTSError IMPORT
IFDEF OS2
EXTRN IntegerOvf_RTSErr : FAR
RUN_ON_PC = 0
ELSE
EXTRN L__Terminate__RTSMain : FAR
EXTRN IntegerOvf__RTSError : FAR
RUN_ON_PC = 1
ENDIF
INCLUDE ..\rts\rts.inc
MINSIZ EQU 8
OSize EQU 0
OFPtr EQU 2
OBPtr EQU 4
OESize EQU -2
DMSRCH EQU 0
DMSize EQU DMSRCH + 2
DMHEAD EQU DMSize + 2
DMSTART EQU DMHEAD + 0AH
DMHDSZ EQU DMSTART + 2
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__16jun87_1952_OF_DynMem DW 0AED0H,4A8H,0
MODULE_TABLE_DATA ENDS
IFDEF MEDIUM
DGROUP GROUP MODULE_TABLE_DATA;
ENDIF
DynMem_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:DynMem_TEXT
ASSUME DS:NOTHING
$BM__DynMem:
;-----------------------------------------------------------
L__InstallDynMem__DynMem PROC FAR
;-----------------------------------------------------------
; in : ( a : ADDRESS; size : CARDINAL )
;
; We assume that the offset is 0
PUSH BP
MOV BP,SP
IFDEF OS2
LDS DI,8[BP] ; DS:DX <= a
MOV SI,DI
ADD SI,DMSTART
MOV BX,DI
ADD BX,DMHEAD
ELSE
LDS BX,8[BP] ; DS:DX <= a
OR BX, BX ; is realy the offset 0
JE I0
MOV AX, BAD_OPERAND
PUSH AX
CALL L__Terminate__RTSMain ; bad address for DynMem
I0:
MOV SI,DMSTART
MOV BX,DMHEAD
ENDIF
MOV WORD PTR OSize[BX],0
MOV WORD PTR OFPtr[BX],SI
MOV WORD PTR OBPtr[BX],SI
MOV WORD PTR 6[BX],0
MOV WORD PTR 8[BX],-1
MOV AX, 6[BP] ; AX <= size
CMP AX, 07FFEH ; is size correct ( < MaxInt )
JB I1
IFDEF OS2
CALL IntegerOvf_RTSErr
ELSE
CALL IntegerOvf__RTSError
ENDIF
I1:
SUB AX, DMHDSZ ; get the current usable size
IFDEF OS2
MOV WORD PTR DMSize[DI], AX ; save the total free size
ELSE
MOV WORD PTR DS:[DMSize], AX ; save the total free size
ENDIF
MOV WORD PTR OSize[SI],AX
MOV WORD PTR OFPtr[SI],BX
MOV WORD PTR OBPtr[SI],BX
ADD SI,AX ; SI <= ^upper limit word
MOV WORD PTR [SI],-1
MOV WORD PTR OESize[SI],AX
IFDEF OS2
MOV WORD PTR DMSRCH[DI],BX
ELSE
MOV WORD PTR DS:[DMSRCH],BX
ENDIF
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 6
L__InstallDynMem__DynMem ENDP
;-----------------------------------------------------------
L__Alloc__DynMem PROC FAR
;-----------------------------------------------------------
; in : ( block : ADDRESS; VAR a : ADDRESS; size : CARDINAL )
;
PUSH BP
MOV BP,SP
IFDEF OS2
LDS SI,0CH[BP] ; DS:OFFSET <= block
ELSE
LDS BX,0CH[BP] ; DS:0 <= block
OR BX,BX
JE L0
MOV AX, BAD_OPERAND
PUSH AX
CALL L__Terminate__RTSMain ; bad address for DynMem
L0:
ENDIF
MOV AX,6[BP] ; AX <= size
; Clear interrupts to prevent access to non reentrant code
PUSHF
IFNDEF OS2
CLI
ENDIF
; calculate length of space to allocate
ADD AX,4 ; Space for control words
CMP AX,MINSIZ ; The bloc must be a minimum size
JGE L4
MOV AX,MINSIZ
; Search for 1st space that is large enough
IFDEF OS2
L4: MOV DX,DMSRCH[SI] ; Start of search
ELSE
L4: MOV DX,DS:[DMSRCH] ; Start of search
ENDIF
MOV BX,DX ; Start of list head
L5: CMP OSize[BX],AX ; Is this bloc large enough ?
JGE L10
CMP WORD PTR OFPtr[BX],DX ; No, end of memory
JE L90
MOV BX,OFPtr[BX] ; Next block
JMP L5
; We have found a block that is large enough
L10: MOV CX,OFPtr[BX] ; Next search begins here
IFDEF OS2
MOV DMSRCH[SI],CX
ELSE
MOV DS:[DMSRCH],CX
ENDIF
MOV CX,OSize[BX] ; Size of the block
SUB CX,AX ; Remainder size
CMP CX,MINSIZ ; .. large enough ?
JGE L15
; Allocate all of block
ADD AX,CX
MOV SI,OFPtr[BX] ; Remove block from list
MOV DI,OBPtr[BX]
MOV OFPtr[DI],SI
MOV OBPtr[SI],DI
JMP L20
; Link remaining block to list
L15: MOV SI,BX ; Block address
ADD SI,AX ; Start address of remaining block
MOV OSize[SI],CX
MOV DI,SI
ADD DI,CX
SUB DI,2 ; Address of end of block
MOV OSize[DI],CX
MOV DX,OFPtr[BX] ; Set new block pointers
MOV OFPtr[SI],DX
MOV DX,OBPtr[BX]
MOV OBPtr[SI],DX
MOV DI,OFPtr[BX] ; Update previous and next block pntrs
MOV OBPtr[DI],SI
MOV DI,OBPtr[BX]
MOV OFPtr[DI],SI
; Allocate block
L20: MOV OSize[BX],AX ; Block size
NEG WORD PTR OSize[BX] ; Mark block unavailable
MOV SI,BX
ADD SI,AX
SUB SI,2 ; Address of end control word
MOV OSize[SI],AX ; Block size
NEG WORD PTR OSize[SI] ; Set unavailable
ADD BX,2 ; Address of data block allocated
; Updates the pointer parametre : RETURN value
L40:
LES AX,8[BP] ; Address of the pointer
XCHG BX,AX
MOV ES:[BX],AX
MOV ES:2[BX],DS
; Restore interrupts as they were before
IFDEF OS2
POPFF
ELSE
POPF
ENDIF
; Modula compatible return
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 0AH
; Error - no block large enough
L90:
MOV BX,0H
MOV DS,BX
DEC BX ; DS:BX <= NIL = 0:FFFFH
JMP L40
L__Alloc__DynMem ENDP
;-----------------------------------------------------------
L__DeAlloc__DynMem PROC FAR
;-----------------------------------------------------------
; in : ( block : ADDRESS; VAR a : ADDRESS; size: CARDINAL ): BOOLEAN;
PUSH BP
MOV BP,SP
; Clears interrupt to protect non reentrant code
PUSHF
IFDEF OS2
LDS AX,0CH[BP] ; DS:0 <= block
ELSE
CLI
LDS BX,0CH[BP] ; DS:0 <= block
OR BX,BX
JE K0
MOV AX, BAD_OPERAND
PUSH AX
CALL L__Terminate__RTSMain ; bad address for DynMem
ENDIF
K0:
LES BX,8[BP] ; Address of the pointer
MOV WORD PTR ES:[BX]+2,0H ; Segment NIL
MOV CX,ES:[BX] ; Get offset of the block
MOV WORD PTR ES:[BX],0FFFFH ; Offset NIL
MOV BX,CX
; MOV CX,6[BP] ; Size of the block
; Get address of variable start
SUB BX,2
CMP WORD PTR OSize[BX],0 ; Is memory allocated
JL K2
; The block is already deallocated
JMP K30
K2:
NEG WORD PTR OSize[BX] ; Length of disposed block
; Merge with previous block if it is available
CMP WORD PTR OESize[BX],0
JL K10
MOV SI,BX ; It is available, calculate its addr.
SUB SI,OESize[BX]
IFDEF OS2
XCHG AX,BX
CMP DMSRCH[BX],SI ; Does search start here
XCHG AX,BX
ELSE
CMP DS:[DMSRCH],SI ; Does search start here
ENDIF
JNE K5
MOV DX,DMHEAD
IFDEF OS2
ADD DX,AX
XCHG AX,BX
MOV DMSRCH[BX],DX
XCHG AX,BX
ELSE
MOV DS:[DMSRCH],DX
ENDIF
K5:
MOV CX,[SI] ; Length of previous block
ADD CX,[BX] ; Length of combined block
MOV BX,SI ; Address of combined block
MOV OSize[BX],CX ; Load new length
MOV SI,OFPtr[BX]
MOV DI,OBPtr[BX]
MOV OFPtr[DI],SI
MOV OBPtr[SI],DI
; Merge with next block if it is available
K10: MOV SI,BX
ADD SI,OSize[BX]
CMP WORD PTR OSize[SI],0 ; Is it available
JL K20
IFDEF OS2
XCHG AX,BX
CMP DMSRCH[BX],SI ; Yes - does search start here
XCHG AX,BX
ELSE
CMP DS:[DMSRCH],SI ; Yes - does search start here
ENDIF
JNE K15
MOV DX,DMHEAD ; Yes - reset search start
IFDEF OS2
ADD DX,AX
XCHG AX,BX
MOV DMSRCH[BX],DX
XCHG AX,BX
ELSE
MOV DS:[DMSRCH],DX
ENDIF
K15:
MOV CX,[SI] ; Length of next block
ADD OSize[BX],CX ; Length of combined block
MOV DI,OBPtr[SI]
MOV SI,OFPtr[SI]
MOV OFPtr[DI],SI
MOV OBPtr[SI],DI
; Link resulting block at beginning of free list
K20:
MOV SI,BX
MOV CX,OSize[BX]
ADD SI,CX
SUB SI,2
MOV [SI],CX ; Put size at end of free block
MOV SI,DMHEAD ; List head offset
IFDEF OS2
ADD SI,AX
ENDIF
MOV CX,OFPtr[SI]
MOV OFPtr[BX],CX
MOV OFPtr[SI],BX
MOV SI,OFPtr[BX] ; Address of next block
MOV CX,OBPtr[SI] ; Next block backward pointer
MOV OBPtr[SI],BX
MOV OBPtr[BX],CX ; Original backward pointer
; Return
K30:
; LES BX, 8[BP] ; DS:BX <= ^a
; MOV WORD PTR ES:[BX],0FFFFH
; MOV WORD PTR ES:2[BX],0H ; a <= NIL
; Test if the block is now empty
IFDEF OS2
XCHG AX, SI
MOV AX, 0
MOV BX, WORD PTR DMSize[SI] ; get total allocatable size
CMP BX, WORD PTR DMSTART[SI] ; is the space totaly free ?
ELSE
MOV AX, 0
MOV BX, WORD PTR DS:[DMSize] ; get total allocatable size
CMP BX, WORD PTR DS:[DMSTART] ; is the space totaly free ?
ENDIF
JNE K40
INC AX
K40:
IFDEF OS2
POPFF
ELSE
POPF
ENDIF
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 0AH
L__DeAlloc__DynMem ENDP
;-----------------------------------------------------------
L__Avail__DynMem PROC FAR
;-----------------------------------------------------------
; in : ( block : ADDRESS; size : CARDINAL ) : BOOLEAN;
PUSH BP
MOV BP,SP
LDS BX, 8[BP] ; DS:0 <= block
IFNDEF OS2
OR BX,BX
JE M0
MOV AX, BAD_OPERAND
PUSH AX
CALL L__Terminate__RTSMain ; bad address for DynMem
ENDIF
M0:
MOV AX, 6[BP]
; Clear interrupts to prevent access to non reentrant code
PUSHF
IFNDEF OS2
CLI
ENDIF
; calculate length of space to allocate
ADD AX,4 ; Space for control words
CMP AX,MINSIZ ; The bloc must be a minimum size
JGE M4
MOV AX,MINSIZ
; Search for 1st space that is large enough
M4: MOV DX,DS:[DMSRCH] ; Start of search
MOV BX,DX ; Start of list head
M5: CMP OSize[BX],AX ; Is this bloc large enough ?
JGE M10
CMP WORD PTR OFPtr[BX],DX ; No, end of memory
JE M90
MOV BX,OFPtr[BX] ; Next block
JMP M5
; We have found a block that is large enough
M10:
MOV AX,1 ; TRUE, the space is svailable
; Restore interrupts as they were before
M80:
IFDEF OS2
POPFF
ELSE
POPF
ENDIF
; Modula compatible return
IFDEF MEDIUM
MOV BX, DGROUP
MOV DS, BX
ENDIF
POP BP
RET 6
; No block large enough
M90:
MOV AX,0
JMP M80
L__Avail__DynMem ENDP
$INIT__DynMem PROC FAR
RET
$INIT__DynMem ENDP
$EM__DynMem:
DynMem_TEXT ENDS
END

View File

@ -0,0 +1,630 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* Longs, imported when LONGINT are used *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
name Longs
; list of exported procedures
; LONGSETS
public pushLSet__Longs
public areSetsEQ__Longs
public superSet__Longs
public subSet__Longs
public union__Longs
public intersection__Longs
public complement__Longs
public unionCompl__Longs
; LONGINTEGER
public LMult__Longs
public LMultU__Longs
public LDiv__Longs
;INITIALIZATION
public $INIT__Longs
PUBLIC KEY__05feb87_1233_OF_Longs
PUBLIC $OK__05feb87_1233_OF_Longs
KEY__05feb87_1233_OF_Longs EQU 0
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__05feb87_1233_OF_Longs DW 0AE45H,2F1H,0
MODULE_TABLE_DATA ENDS
Longs_TEXT SEGMENT BYTE PUBLIC 'CODE' ; Program Code Segment
assume cs:Longs_TEXT
pushLSet__Longs proc far
;***************************************************************************
;* The procedure pushes a longset on the stack *
;* *
;* parameters IN : address of set :DS:SI *
;* : length of set in bytes : CX *
;* *
;* OUT : none *
;***************************************************************************
pop ax ;save return address
pop bx
inc cx ;round to next greater
and cx, 0FEH ; even number
sub sp, cx ;allocate space on stack
push bx ;push return address on
push ax ; top of stack
mov ax, ss ;load destination pointer
mov es, ax
mov di, sp
add di, 4
mov ax, cx ;save number of bytes
sar cx, 1 ;#bytes -> #words
cld ;addresses are incremented
rep movsw
sub si, ax ;restore pointer
ret
pushLSet__Longs endp
areSetsEQ__Longs proc far
;***************************************************************************
;* The procedure compares two sets on equality *
;* *
;* parameters IN : address of set1 : DS:SI *
;* address of set2 : ES:DI *
;* : length of set in bytes : CX *
;* *
;* OUT : result : AX (0=NOT EQUAL 1=EQUAL) *
;***************************************************************************
sar cx, 1 ;next smaller # of words
cld ;incremental compare
repe cmpsw
jne not_EQ
test ax, 1 ;test if odd # of bytes
je _EQ ;even # -> only cmpsw
cmpsb ;compare last byte
jne not_EQ
_EQ: mov ax, 1
jmp done_eq
not_EQ: xor ax, ax
done_eq: ret
areSetsEQ__Longs endp
superSet__Longs proc far
;***************************************************************************
;* The procedure evaluates if A is super set of B (A>=B) *
;* i.e all elements of B are included in A *
;* parameters IN : set A : DS:SI *
;* set B : ES:DI *
;* parameters OUT : result is passed in AX (0 = FALSE 1 = TRUE) *
;***************************************************************************
push ax ;save odd/even-flag
sar cx, 1 ;next smaller # of words
cld
load1: lodsw ;load sourceword and INC SI
not ax
and ax, es:[di] ;if result<> 0 -> not incl.
jnz _pop
inc di ;next destination word
inc di
loop load1
pop ax ;restore odd/even-flag
test ax, 1 ;test if odd # of bytes
jz incl ;even # -> comp completed
lodsb ;load last byte
not al
and al, es:[di]
jnz not_incl
incl: mov ax, 1
jmp done_incl
_pop: pop ax ;remove odd/even
; flag from stack
not_incl: xor ax, ax
done_incl: ret
superSet__Longs endp
subSet__Longs proc far
;***************************************************************************
;* evaluates if A is subSet of B (A>=B) *
;* i.e all elements of A are included in B *
;* parameters IN : set A : ES:DI *
;* set B : DS:SI *
;* parameters OUT : result is passed in AX (0 = FALSE 1 = TRUE) *
;***************************************************************************
push ax ;save odd/even-flag
sar cx, 1 ;next smaller # of words
cld
load6: lodsw ;load sourceword and INC SI
not ax
and ax, es:[di] ;if result<> 0 -> not incl.
jnz _pop
inc di ;next destination word
inc di
loop load6
pop ax ;restore odd/even-flag
test ax, 1 ;test if odd # of bytes
jz incl2 ;even # -> comp completed
lodsb ;load last byte
not al
and al, es:[di]
jnz not_incl2
incl2: mov ax, 1
jmp done_incl2
pop2: pop ax ;remove odd/even
; flag from stack
not_incl2: xor ax, ax
done_incl2: ret
subSet__Longs endp
union__Longs proc far
;***************************************************************************
;* The procedure forms the union of 2 sets B := A+B *
;* parameters IN : set A : ES:DI *
;* set B : DS:SI *
;* length in bytes : CX *
;* *
;* parameters OUT : set B contains the result *
;***************************************************************************
push ax ;saving of odd/even flag
sar cx, 1 ;next smaller # of words
cld
load2: lodsw ;load source-op in AX
or es:[di], ax
inc di ;destination pointer to
inc di ; next word
loop load2
pop ax
test ax, 1 ;check if odd # of bytes
jz union_done
lodsb ;load last byte
or es:[di], al
union_done: ret
union__Longs endp
intersection__Longs proc far
;***************************************************************************
;* The procedure forms the intersection of 2 sets B := A*B *
;* parameters IN : set A : ES:DI *
;* set B : DS:SI *
;* length in bytes : CX *
;* *
;* parameters OUT : set B contains the result *
;***************************************************************************
push ax ;saving of odd/even flag
sar cx, 1 ;next smaller # of words
cld
load3: lodsw ;load source-op in AX
and es:[di], ax
inc di ;destination pointer to
inc di ; next word
loop load3
pop ax
test ax, 1 ;check if odd # of bytes
jz intersec_done
lodsb ;load last byte
and es:[di], al
intersec_done: ret
intersection__Longs endp
complement__Longs proc far
;***************************************************************************
;* The procedure forms the difference of 2 sets B := A-B *
;* parameters IN : set A : ES:DI *
;* set B : DS:SI *
;* length in bytes : CX *
;* *
;* parameters OUT : set B contains the result *
;***************************************************************************
push ax ;saving of odd/even flag
sar cx, 1 ;next smaller # of words
cld
load4: lodsw ;load source-op in AX
not ax ;c := (a) and (not (b))
and es:[di], ax
inc di ;destination pointer to
inc di ; next word
loop load4
pop ax
test ax, 1 ;check if odd # of bytes
jz compl_done
lodsb ;load last byte
not al
and es:[di], al
compl_done: ret
complement__Longs endp
unionCompl__Longs proc far
;***************************************************************************
;* The procedure forms the symmetric difference of 2 sets B := A-B *
;* parameters IN : set A : ES:DI *
;* set B : DS:SI *
;* length in bytes : CX *
;* *
;* parameters OUT : set B contains the result *
;***************************************************************************
push ax ;saving of odd/even flag
sar cx, 1 ;next smaller # of words
cld
load5: lodsw ;load source-op in AX
xor es:[di], ax
inc di ;destination pointer to
inc di ; next word
loop load5
pop ax
test ax, 1
;check if odd # of bytes
jz uni_Compl_done
lodsb ;load last byte
xor es:[di], al
uni_Compl_done: ret
unionCompl__Longs endp
LMult__Longs proc far
;***************************************************************************
; multiplication of 2 32bit signed numbers
;
; high part of multiplicant [bp+12]
; low part of multiplicant [bp+10]
; high part of multiplier [bp+8]
; low part of multiplier [bp+6]
;
; dx and cx used ---> they will be saved by compiler if needed
; product returned in bx,ax (high to low order)
;***************************************************************************
;
push bp
mov bp, sp
xor cx, cx ;negflag (cx) = 0
cmp word ptr [bp+12], 0 ;
jns not_minus ;is 1st operand neg?
neg word ptr [bp+12] ;generating of 2s complement
neg word ptr [bp+10] ;
sbb word ptr [bp+12],0 ;
not cx ;
not_minus: cmp word ptr [bp+8], 0 ;is 2nd operand neg?
jns go_mul
neg word ptr [bp+8] ;generating of 2s complement
neg word ptr [bp+6] ;
sbb word ptr [bp+8],0 ;
not cx ;
;performing of the unsigned multiplication
go_mul: cmp word ptr [bp+12], 0 ;if hi1 = 0 then
jne hi1diff0 ;
cmp word ptr [bp+8], 0 ;if hi2 = 0 then
jne hi2diff0
;here hi1=hi2=0
mov ax, word ptr [bp+6] ;ax := lo2
mul word ptr [bp+10] ;(dx,ax) := lo1 * lo2
jmp mult_done
;here hi1=0 & hi2#0
hi2diff0: mov ax, word ptr [bp+10] ;ax := lo1
mul word ptr [bp+6] ;(dx,ax) := lo1 * lo2
push dx ;
push ax ;
mov ax, word ptr [bp+10] ;ax := lo1
mul word ptr [bp+8] ;(dx,ax) := lo1 * hi2
jb mult_ovflw ;if dx <> 0 then ovflw
pop bx ;bx := prev ax
pop dx ;dx := prev dx
add dx, ax
xchg ax, bx
jb mult_ovflw
jmp mult_done
;here h1#0
hi1diff0: cmp word ptr [bp+8], 0 ;if hi2=0 then
jne mult_ovflw
mov ax, word ptr [bp+10] ;ax := lo1
mul word ptr [bp+6] ;(dx,ax) := lo1 * lo2
push dx ;
push ax ;
mov ax, word ptr [bp+6] ;ax := lo2
mul word ptr [bp+12] ;(dx,ax) := hi1 * lo2
jb mult_ovflw ;if dx <> 0 then ovflw
pop bx
pop dx
add dx, ax
xchg ax, bx
jb mult_ovflw
;adjusting of the sign of the result
mult_done: cmp dx, 0
js verify_min
cmp cx, 0
jne change_sign
clc
jmp mult_ok
change_sign: neg dx
neg ax
sbb dx, 0
clc
mult_ok: xchg bx, dx
mov sp, bp
pop bp
ret 8
verify_min: cmp cx, 0
jz mult_ovflw
cmp dx, 8000h
jne mult_ovflw
cmp ax, 0
clc
jz mult_ok
mult_ovflw: stc
jmp mult_ok
LMult__Longs endp
LMultU__Longs proc far
;***************************************************************************
; multiplication of 2 32bits unsigned numbers + no overflow tests
;
; high part of multiplicant [bp+12]
; low part of multiplicant [bp+10]
; high part of multiplier [bp+8]
; low part of multiplier [bp+6]
;
; dx and cx used ---> they will be saved by compiler if needed
; product returned in bx,ax (high to low order)
;***************************************************************************
;
push bp
mov bp, sp
cmp word ptr [bp+12], 0 ;if hi1 = 0 then
jne hi1dif0 ;
cmp word ptr [bp+8], 0 ;if hi2 = 0 then
jne hi2dif0 ;
;here hi1=hi2=0
mov ax, word ptr [bp+6] ;ax := lo2
mul word ptr [bp+10] ;(dx,ax) := lo1 * lo2
xchg bx, dx
jmp lmult_done
;here hi1=0 & hi2#0
hi2dif0: mov ax, word ptr [bp+10] ;ax := lo1
mul word ptr [bp+6] ;(dx,ax) := lo1 * lo2
mov cx, ax
mov bx, dx
mov ax, word ptr [bp+10] ;ax := lo1
mul word ptr [bp+8] ;(dx,ax) := lo1 * hi2
add bx, ax
xchg ax, cx
jmp lmult_done
;here hi1#0
hi1dif0: cmp word ptr [bp+8], 0 ;if hi2#0 then
jne hi12dif0
;here hi1#0 & hi2=0
mov ax, word ptr [bp+10] ;ax := lo1
mul word ptr [bp+6] ;(dx,ax) := lo1 * lo2
mov cx, ax
mov bx, dx
mov ax, word ptr [bp+6] ;ax := lo2
mul word ptr [bp+12] ;(dx,ax) := hi1 * lo2
add bx, ax
xchg ax, cx
jmp lmult_done
hi12dif0: ;here hi1#0 & hi2#0
mov ax, word ptr [bp+8] ;ax := hi2
mul word ptr [bp+10] ;(dx,ax) := hi2 * lo1
mov bx, ax
mov ax, word ptr [bp+6] ;ax := lo2
mul word ptr [bp+12] ;(dx,ax) := lo2 * hi1
add bx, ax
mov ax, word ptr [bp+6] ;ax := lo2
mul word ptr [bp+10] ;(dx,ax) := lo2 * lo1
add bx, dx
lmult_done: mov sp, bp
pop bp
ret 8
LMultU__Longs endp
LDiv__Longs proc far
;***************************************************************************
;PARAMETERS IN:
;dividend_hi : on top of stack [bp+12]
;dividend_lo : next word on stack [bp+10]
;divisor_hi : next word on stack [bp+08]
;divisor_lo : next word on stack [bp+06]
;
;PARAMETERS OUT:
;quotient low : BX
;quotient high : CX
;remainder low : AX
;remainder high: DX
;***************************************************************************
;
push bp ;save bp on stack
mov bp,sp ;bp := sp
push si ;save si on stack
push di ;save di on stack
xor si,si ;si(gn indicator) := 0
Check_1: mov ax,[bp+12] ;if dividend_hi is negative then
test ax,ax ;change sign and negate
jge Check_2 ;si(gn indicator).
not si ;si := NOT(si)
mov dx,[bp+10] ;dx := dividend_lo
neg ax ;negate dividend_hi
neg dx ;negate dividend_lo
sbb ax,00 ;subtract dividend_hi by borrow
mov [bp+10],dx ;move dividend back to
mov [bp+12],ax ;stack.
Check_2: push si ;save sign of dividend
mov ax,[bp+08] ;If divisor_hi >= 0 then
test ax,ax ; goto Check_3
jg Check_3 ;If divisor_hi = 0 then
je Chk_for_0 ; goto Chk_for_0
not si ;(divisor_hi is neg.) si := NOT(si)
mov dx,[bp+06] ;dx := divisor_lo
neg ax ;negate divisor_hi
neg dx ;negate divisor_lo
sbb ax,00 ;subtract divisor_hi by borrow
mov [bp+06],dx ;move divisor back
mov [bp+08],ax ;to stack
jmp Check_3 ;goto Check_3
Chk_for_0: mov dx,[bp+06] ;if divisor_lo # 0 then
test dx,dx ; goto Check_3
jne Check_3 ;(divisor is zero!)
Set_cf: stc ;Set carry flag
jmp Return ;goto Return
Check_3: test ax,ax ;If divisor > 16Bit Then
jnz Shift_Ops ; goto Shift_Ops.
mov ax,[bp+12] ;if dividend_hi # 8000H then
cmp ax,8000h ; goto Div_Hi
jne Div_Hi ;
cmp si,0 ;if Quotient < 0 then
jnz Div_Hi ; goto Div_Hi
jmp Set_cf ;Goto Set_cf
Div_Hi: mov bx,[bp+06] ;(Division if divisor <= 16 Bit)
xor dx,dx ;dx := 0 (ax := divident_hi)
div bx ;(dx,ax) := Dividend_hi/Divisor_lo
mov cx,ax ;cx := Quotient_hi
mov ax,[bp+10] ;ax := Dividend_lo
div bx ;(dx,ax) := Dividend_lo/Divisor_lo
mov bx,ax ;bx := Quotient_lo
mov ax,dx ;ax := Remainder_lo
xor dx,dx ;dx := Remainder_hi := 0
jmp Adj_Quo ;goto Adj_Quo
Shift_Ops: mov bx,ax ;Shift dividend and divisor to the
mov cx,[bp+06] ;right (divides dividend and
mov dx,[bp+12] ;divisor by two) until divisor is
mov ax,[bp+10] ;smaller than 16 Bit.
Loop_1: shr bx,1 ;
rcr cx,1 ;Dividend => Dividend_sh
shr dx,1 ;Divisor => Divisor_sh
rcr ax,1 ;
test bx,bx ;
jnz Loop_1 ;
Calc_Quot: div cx ;(dx,ax) := Dividend_sh/Divisor_sh
mov di,ax ;Save Quotient in di
xor dx,dx ;
push dx ;Multiply Quotient by Divisor
push ax ;(call LMultU__Longs)
push [bp+08] ;Result will be Dividend_x
push [bp+06] ;
call LMultU__Longs ;
cmp bx,[bp+12] ;If Dividend_x_hi > Dividend_hi then
ja Correct_Res ; goto Correct_Res
jb Calc_Rem2 ;If Dividend_x_hi < Dividend_hi then
cmp ax,[bp+10] ; goto Calc_Rem
jbe Calc_Rem2 ;If Dividend_x_lo <= Dividend_lo then
nop ; goto Calc_Rem
Correct_Res: dec di ;Decrement di by 1 (correct Quotient)
sub ax,[bp+06] ;ax := Dividend_x_lo - Divisor_lo
sbb bx,[bp+08] ;bx := Dividend_X_hi - Divisor_hi
Calc_Rem2: push ax ;Save ax on stack
push bx ;Save bx on stack
mov ax,[bp+10] ;ax := Dividend_lo
mov dx,[bp+12] ;dx := Dividend_hi
sub ax,[bp-08] ;ax := Dividend_lo - Dividend_x_lo
sbb dx,[bp-10] ;dx := Dividend_hi - Dividend_x_hi
mov bx,di ;bx := Quotient_lo
xor cx,cx ;cx := 0
add sp,4 ;correct stack pointer
Adj_Quo: test si,si ;if si(gn indicator) = 0 then
jz Adj_Rem ; goto Adj_Rem
neg cx ;negate Quotient_hi
neg bx ;negate Quotient_lo
sbb cx,00 ;subtract borrow from Quotient_hi
Adj_Rem: pop si ;get sign of Dividend
test si,si ;if Dividend was positiv then
jz Adj_End ; goto Adj_End
neg dx ;negate Remainder_hi
neg ax ;negate Remainder_lo
sbb dx,00 ;subtract borrow from Quotient_hi
Adj_End: clc ;clear carry flag (no error)
Return: pop di ;restore registers
pop si ;and set stack
mov sp,bp ;pointer on entry value.
pop bp ;
ret 8 ;
LDiv__Longs endp
$INIT__Longs proc far ; initialization part
ret
$INIT__Longs endp
Longs_TEXT ENDS
END


View File

@ -0,0 +1,749 @@
;(**************************************************************************)
;(* *)
;(* MODULA-2 Library *)
;(* *)
;(* LOGITECH Inc, Fremont, CA 94555 (USA) *)
;(* *)
;(* Module : *)
;(* Strings, operations on strings *)
;(* *)
;(* Release : Dec 89 *)
;(* *)
;(* Copyright (C) 1987, 1989 Logitech, All rights reserved *)
;(* *)
;(* Permission is hereby granted to registered users to use or abstract *)
;(* the following program in the implementation of customized versions. *)
;(* This permission does not include the right to redistribute the *)
;(* source code of this program. *)
;(* *)
;(**************************************************************************)
TITLE Strings
.RADIX 16
PUBLIC L__ConstAssign__Strings
PUBLIC L__Assign__Strings
PUBLIC L__Insert__Strings
PUBLIC L__Delete__Strings
PUBLIC L__Pos__Strings
PUBLIC L__Copy__Strings
PUBLIC L__Concat__Strings
PUBLIC L__Length__Strings
PUBLIC L__CompareStr__Strings
PUBLIC $INIT__Strings
PUBLIC KEY__10aug87_2031_OF_Strings
PUBLIC $OK__31jul87_1000_OF_Strings
KEY__10aug87_2031_OF_Strings EQU 0
IFDEF OS2
EXTRN DynParCopy_RTSLang:FAR
ELSE
EXTRN DynParCopy__RTSLanguage:FAR
ENDIF
MODULE_TABLE_DATA SEGMENT WORD PUBLIC 'FAR_DATA'
$OK__31jul87_1000_OF_Strings DW 0AEFFH,0258H,0
MODULE_TABLE_DATA ENDS
IFDEF MEDIUM
DGROUP GROUP MODULE_TABLE_DATA
ENDIF
Strings_TEXT SEGMENT BYTE PUBLIC 'CODE'
ASSUME CS:Strings_TEXT
ASSUME DS:NOTHING
$BM__Strings:
;
; PROCEDURE Length (VAR str: ARRAY OF CHAR): CARDINAL;
;
L__Length__Strings PROC FAR
PUSH BP
MOV BP,SP
MOV CX,[BP+000AH]
INC CX
MOV AL,0
CLD
LES DI,[BP+0006H]
REPNZ SCASB
JNE $33
DEC DI
$33:
MOV AX,DI
SUB AX,[BP+0006H]
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 0006H
L__Length__Strings ENDP
;
; PROCEDURE ConstAssign (source : ARRAY OF CHAR;
; VAR destination : ARRAY OF CHAR);
;
L__ConstAssign__Strings PROC FAR
PUSH BP
MOV BP,SP
MOV DI,000CH
MOV CX,0001
IFDEF OS2
CALL DynParCopy_RTSLang
ELSE
CALL DynParCopy__RTSLanguage
ENDIF
PUSH [BP+0010H]
LES BX,[BP+000CH]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV CX,AX
MOV AX,[BP+000AH]
INC AX
CLD
CMP AX,CX
JA $00
MOV CX,AX
$00: MOV BX,CX
LES DI,[BP+0006]
JCXZ $01
LDS SI,[BP+000CH]
REPNZ MOVSB
$01: CMP AX,BX
JNA $02
MOV BYTE PTR ES:[DI],0
$02:
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 000CH
L__ConstAssign__Strings ENDP
;
; PROCEDURE Assign (VAR source : ARRAY OF CHAR;
; VAR destination : ARRAY OF CHAR);
;
L__Assign__Strings PROC FAR
PUSH BP
MOV BP,SP
PUSH [BP+0010H]
LES BX,[BP+000CH]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV CX,AX
MOV AX,[BP+000AH]
INC AX
CLD
CMP AX,CX
JA $10
MOV CX,AX
$10: MOV BX,CX
LES DI,[BP+0006H]
JCXZ $11
LDS SI,[BP+000CH]
REPNZ MOVSB
$11:
CMP AX,BX
JBE $12
MOV BYTE PTR ES:[DI],0
$12:
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 000CH
L__Assign__Strings ENDP
;
; PROCEDURE Insert (substr: ARRAY OF CHAR;
; VAR str: ARRAY OF CHAR;
; inx: CARDINAL);
;
L__Insert__Strings PROC FAR
PUSH BP
MOV BP,SP
SUB SP,6
MOV DI,000EH
MOV CX,0001H
IFDEF OS2
CALL DynParCopy_RTSLang
ELSE
CALL DynParCopy__RTSLanguage
ENDIF
; y:= Length(substr);
PUSH [BP+0012H]
LES BX,[BP+000EH]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV [BP-0004H],AX
; IF y <> 0 THEN
TEST AX,AX
JNE $13
JMP $14
$13:
; x:=Length(str); (* len of destination *)
PUSH [BP+000CH]
LES BX,[BP+0008H]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV [BP-0006H],AX
; IF inx > x THEN
MOV CX,[BP+0006H]
CMP CX,AX
JBE $15
; inx:=x (* adjust 'inx' to len of 'str' *)
MOV [BP+0006H],AX
$15:
; END;
; IF x+y <= HIGH(str) THEN
MOV AX,[BP-0006H]
ADD AX,[BP-0004H]
CMP AX,[BP+000CH]
JNBE $16
; str[x+y]:=EOS (* set EOS at end of sum of strings *)
LES BX,[BP+0008H]
MOV SI,AX
MOV BYTE PTR ES:[BX+SI],0
$16:
; END;
; IF y > HIGH(str)+1-inx THEN
MOV AX,[BP+000CH]
INC AX
SUB AX,[BP+0006H]
CMP [BP-0004H],AX
JBE $17
; y:=HIGH(str)+1-inx; (* adjust y to remaining len *)
MOV [BP-0004H],AX
$17:
; END;
; IF x > HIGH(str)+1-y THEN
MOV AX,[BP+000CH]
INC AX
SUB AX,[BP-0004H]
CMP [BP-0006H],AX
JBE $18
; z:=HIGH(str)+1-inx-y;
SUB AX,[BP+0006H]
MOV [BP-0002H],AX
JMP SHORT $19
$18:
; ELSE
; z:=x-inx;
MOV AX,[BP-0006H]
SUB AX,[BP+0006H]
MOV [BP-0002H],AX
$19:
; END;
; x:=inx+z;
ADD AX,[BP+0006H]
MOV [BP-0006H],AX
MOV CX,[BP-0002H]
CLD
JCXZ $20
LDS SI,[BP+0008H]
ADD SI,[BP-0006H]
DEC SI
PUSH DS
POP ES
MOV DI,SI
ADD DI,[BP-0004H]
STD
REPNZ MOVSB
CLD
$20:
MOV CX,[BP-0004H]
JCXZ $21
LDS SI,[BP+000EH]
LES DI,[BP+0008H]
ADD DI,[BP+0006H]
REPNZ MOVSB
$14:
$21:
; END;
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 000EH
L__Insert__Strings ENDP
;
; PROCEDURE Delete (VAR str: ARRAY OF CHAR;
; inx: CARDINAL;
; len: CARDINAL);
;
L__Delete__Strings PROC FAR
PUSH BP
MOV BP,SP
PUSH [BP+000EH]
LES BX,[BP+000AH]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV CX,AX
CLD
CMP WORD PTR [BP+0006H],0
JE $22
SUB CX,[BP+0008H]
JBE $22
LES DI,[BP+000AH]
ADD DI,[BP+0008H]
SUB CX,[BP+0006H]
JBE $23
MOV SI,DI
PUSH ES
POP DS
ADD SI,[BP+0006H]
REPNZ MOVSB
$23:
MOV BYTE PTR ES:[DI],0
$22:
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 000AH
L__Delete__Strings ENDP
;
; PROCEDURE Pos (substr, str: ARRAY OF CHAR): CARDINAL;
;
L__Pos__Strings PROC FAR
PUSH BP
MOV BP,SP
SUB SP,0006H
; MOV DI,000CH
; MOV CX,0001H
; CALL DynParCopy_RTSLang
; MOV DI,0006H
; MOV CX,0001H
; CALL DynParCopy_RTSLang
; lsub := Length(substr);
PUSH [BP+0010H]
LES BX,[BP+000CH]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV [BP-0004H],AX
; ls := Length(str);
PUSH [BP+000AH]
LES BX,[BP+0006H]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV [BP-0002H],AX
; IF (lsub <> 0) THEN
CMP WORD PTR [BP-0004H],0
JE $24
; i := 0;
MOV WORD PTR [BP-0006H],0
$26:
; WHILE i + lsub <= ls DO
MOV AX,[BP-0006H]
ADD AX,[BP-0004H]
CMP AX,[BP-0002H]
JNBE $24
MOV CX,[BP-0004H]
CLD
LDS SI,[BP+0006H]
LES DI,[BP+000CH]
ADD SI,[BP-0006H]
REPE CMPSB
JNE $25
MOV AX,[BP-0006H]
$27:
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 000CH
$25:
INC WORD PTR [BP-0006H]
JMP $26
$24:
; RETURN HIGH(str)+1
MOV AX,[BP+000AH]
INC AX
JMP $27
L__Pos__Strings ENDP
;
; PROCEDURE Copy (str: ARRAY OF CHAR;
; inx: CARDINAL;
; len: CARDINAL;
; VAR result: ARRAY OF CHAR);
;
L__Copy__Strings PROC FAR
PUSH BP
MOV BP,SP
PUSH AX
MOV DI,0010H
MOV CX,0001H
IFDEF OS2
CALL DynParCopy_RTSLang
ELSE
CALL DynParCopy__RTSLanguage
ENDIF
; x:= Length(str);
PUSH [BP+0014H]
LES BX,[BP+0010H]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV [BP-0002H],AX
; IF (inx < x) THEN
MOV CX,[BP+000EH]
CMP CX,AX
JNB $28
; IF ((inx + len) > x) THEN
MOV AX,[BP+000EH]
ADD AX,[BP+000CH]
CMP AX,[BP-0002H]
JBE $29
; len:= x-inx;
MOV AX,[BP-0002H]
SUB AX,[BP+000EH]
MOV [BP+000C],AX
$29:
; END;
; IF (len > (HIGH(result)+1)) THEN
MOV AX,[BP+000AH]
INC AX
CMP [BP+000CH],AX
JBE $30
; len:= HIGH(result)+1;
MOV [BP+000CH],AX
$30:
; END;
MOV CX,[BP+000CH]
CLD
LES DI,[BP+0006H]
JCXZ $31
LDS SI,[BP+0010H]
ADD SI,[BP+000EH]
REPNZ MOVSB
$31:
MOV CX,[BP+000CH]
CMP CX,[BP+000AH]
JNBE $32
MOV BYTE PTR ES:[DI],0
JMP SHORT $32
$28:
; ELSE (* 'inx' points after end of string *)
LES DI,[BP+0006H]
MOV BYTE PTR ES:[DI],0
$32:
; END;
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 0010H
L__Copy__Strings ENDP
;
; PROCEDURE Concat (s1, s2: ARRAY OF CHAR;
; VAR result: ARRAY OF CHAR);
;
L__Concat__Strings PROC FAR
PUSH BP
MOV BP,SP
MOV DI,0012H
MOV CX,0001H
IFDEF OS2
CALL DynParCopy_RTSLang
ELSE
CALL DynParCopy__RTSLanguage
ENDIF
MOV DI,000CH
MOV CX,0001H
IFDEF OS2
CALL DynParCopy_RTSLang
ELSE
CALL DynParCopy__RTSLanguage
ENDIF
; Assign(s1,result);
PUSH [BP+0016H]
LES BX,[BP+0012H]
PUSH ES
PUSH BX
PUSH [BP+000AH]
LDS SI,[BP+0006H]
PUSH DS
PUSH SI
CALL L__Assign__Strings
; Insert(s2,result,Length(s1))
PUSH [BP+0010H]
LES BX,[BP+000CH]
PUSH ES
PUSH BX
PUSH [BP+000AH]
LDS SI,[BP+0006H]
PUSH DS
PUSH SI
PUSH [BP+0016H]
LES DI,[BP+0012H]
PUSH ES
PUSH DI
CALL L__Length__Strings
PUSH AX
CALL L__Insert__Strings
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 0012H
L__Concat__Strings ENDP
;
; PROCEDURE CompareStr (s1, s2: ARRAY OF CHAR): INTEGER;
;
L__CompareStr__Strings PROC FAR
PUSH BP
MOV BP,SP
; MOV DI,000CH
; MOV CX,0001H
; CALL DynParCopy_RTSLang
; MOV DI,0006H
; MOV CX,0001H
; CALL DynParCopy_RTSLang
PUSH [BP+000AH]
LES BX,[BP+0006H]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV DX,AX
PUSH DX
PUSH [BP+0010H]
LES BX,[BP+000CH]
PUSH ES
PUSH BX
CALL L__Length__Strings
MOV CX,AX
POP DX
CLD
XOR AX,AX
CMP DX,CX
JE $34
JA $35
MOV AX,0FFFFH
JMP SHORT $34
$35:
MOV CX,DX
MOV AX,0001H
$34:
INC CX
LES DI,[BP+0006H]
LDS SI,[BP+000CH]
REPE CMPSB
JCXZ $36
JNBE $37
MOV AX,0FFFFH
JMP SHORT $36
$37:
MOV AX,0001H
$36:
IFDEF MEDIUM
MOV BX,DGROUP
MOV DS,BX
ENDIF
MOV SP,BP
POP BP
RET 000CH
L__CompareStr__Strings ENDP
;$BODY__Strings PROC FAR
; RET
;$BODY__Strings ENDP
$INIT__Strings PROC FAR
RET
$INIT__Strings ENDP
Strings_TEXT ENDS
END

View File

@ -0,0 +1,47 @@
(* Abbreviation: ASCII *)
(* Version 1.10, Nov 1984 *)
(* spacing modified Feb 12, 1985 *)
DEFINITION MODULE ASCII;
(*
Symbolic constants for non-printing ASCII characters.
This module has an empty implementation.
*)
EXPORT QUALIFIED
nul, soh, stx, etx, eot, enq, ack, bel,
bs, ht, lf, vt, ff, cr, so, si,
dle, dc1, dc2, dc3, dc4, nak, syn, etb,
can, em, sub, esc, fs, gs, rs, us,
del,
EOL;
CONST
nul = 00C; soh = 01C; stx = 02C; etx = 03C;
eot = 04C; enq = 05C; ack = 06C; bel = 07C;
bs = 10C; ht = 11C; lf = 12C; vt = 13C;
ff = 14C; cr = 15C; so = 16C; si = 17C;
dle = 20C; dc1 = 21C; dc2 = 22C; dc3 = 23C;
dc4 = 24C; nak = 25C; syn = 26C; etb = 27C;
can = 30C; em = 31C; sub = 32C; esc = 33C;
fs = 34C; gs = 35C; rs = 36C; us = 37C;
del = 177C;
CONST
EOL = 36C;
(*
- end-of line character
This (non-ASCII) constant defines the internal name
of the end-of-line character. Using this constant has
the advantage, that only one character is used to
specify line ends (as opposed to cr/lf).
The standard I/O modules interpret this character
and transform it into the (sequence of) end-of-line
code(s) required by the device they support. See
definition modules of 'Terminal' and 'FileSystem'.
*)
END ASCII.


View File

@ -0,0 +1,64 @@
DEFINITION MODULE BitBlockOps;
(* Bitwise operations on blocks.
Blocks are defined as a starting address and a size, i.e. the number of
bytes they hold.
In a block, the left or low bit is the low bit of the byte located at
(starting address); and the right or high bit is the high bit of the byte
located at (starting address + size - 1)
*)
FROM SYSTEM IMPORT ADDRESS;
PROCEDURE BlockAnd (destination, source: ADDRESS;
size : CARDINAL);
(* ANDs the block destination with the block source *)
PROCEDURE BlockOr (destination, source: ADDRESS;
size : CARDINAL);
(* Bitwise OR *)
PROCEDURE BlockXor (destination, source: ADDRESS;
size : CARDINAL);
(* Bitwise XOR *)
PROCEDURE BlockNot (block : ADDRESS;
size : CARDINAL);
(* Bitwise complement to 1 *)
PROCEDURE BlockShr (block : ADDRESS;
size : CARDINAL;
count : CARDINAL);
(* Shift Logical Right
shifts the bits in block to the right by the number of bits specified
in count. Zeros are shifted in on the left. *)
PROCEDURE BlockSar (block : ADDRESS;
size : CARDINAL;
count : CARDINAL);
(* Shift Arithmetic Right
shifts the bits in block to the right by the number of bits specified
in count. Bits equal to the original high order bit are shifted in
on the left, preserving the sign of the original value. *)
PROCEDURE BlockShl (block : ADDRESS;
size : CARDINAL;
count : CARDINAL);
(* Shift Left
shifts the bits in block to the left by the number of bits specified
in count. Zeros are shifted in on the right. *)
PROCEDURE BlockRor (block : ADDRESS;
size : CARDINAL;
count : CARDINAL);
(* Rotate Right
rotates block right by the number of bits specified in count *)
PROCEDURE BlockRol (block : ADDRESS;
size : CARDINAL;
count : CARDINAL);
(* Rotate Left
rotates block left by the number of bits specified in count *)
END BitBlockOps.


View File

@ -0,0 +1,74 @@
DEFINITION MODULE BitByteOps;
(* Bitwise operations on bytes.
Bits in bytes are numbered from 0 to 7 *)
FROM SYSTEM IMPORT BYTE;
PROCEDURE GetBits (source : BYTE;
firstBit, lastBit : CARDINAL): BYTE;
(* Extracts the bits of source from firstBit to lastBit and returns
them as a byte in which bit 0 correspond to the firstBit of the
source. *)
PROCEDURE SetBits (VAR byte : BYTE;
firstBit, lastBit: CARDINAL;
pattern : BYTE);
(* Masks byte with pattern from firstBit to lastBit. The first
(lastBit - firstBit + 1 of pattern are used, with leading zeros
if necessary.
Examples : To set the bits to 1, the pattern 0FFH should be passed,
and to set the bits to 0, the pattern 0 should be passed. *)
PROCEDURE ByteAnd (left, right : BYTE): BYTE;
(* Bitwise AND *)
PROCEDURE ByteOr (left, right : BYTE): BYTE;
(* Bitwise OR *)
PROCEDURE ByteXor (left, right : BYTE): BYTE;
(* Bitwise XOR *)
PROCEDURE ByteNot (byte : BYTE): BYTE;
(* Bitwise complement to 1 *)
PROCEDURE ByteShr (byte : BYTE;
count : CARDINAL): BYTE;
(* Shift Logical Right
shifts the bits in byte to the right by the number of bits specified
in count. Zeros are shifted in on the left. *)
PROCEDURE ByteSar (byte : BYTE;
count : CARDINAL): BYTE;
(* Shift Arithmetic Right
shifts the bits in byte to the right by the number of bits specified
in count. Bits equal to the original high order bit are shifted in
on the left, preserving the sign of the original value. *)
PROCEDURE ByteShl (byte : BYTE;
count : CARDINAL): BYTE;
(* Shift Left
shifts the bits in byte to the left by the number of bits specified
in count. Zeros are shifted in on the right. *)
PROCEDURE ByteRor (byte : BYTE;
count : CARDINAL): BYTE;
(* Rotate Right
rotates byte right by the number of bits specified in count *)
PROCEDURE ByteRol (byte : BYTE;
count : CARDINAL): BYTE;
(* Rotate Left
rotates byte left by the number of bits specified in count *)
PROCEDURE HighNibble (byte : BYTE): BYTE;
(* Returns the high order nibble (4 bits) value of byte *)
PROCEDURE LowNibble (byte : BYTE): BYTE;
(* Returns the low order nibble (4 bits) value of byte *)
PROCEDURE Swap (VAR byte : BYTE);
(* Swaps the high and low order nibble values of byte *)
END BitByteOps.


View File

@ -0,0 +1,74 @@
DEFINITION MODULE BitWordOps;
(* Bitwise operations on words.
Bits in words are numbered from 0 to 15 *)
FROM SYSTEM IMPORT WORD;
PROCEDURE GetBits (source : WORD;
firstBit, lastBit : CARDINAL): WORD;
(* Extracts the bits of source from firstBit to lastBit and returns
them as a word in which bit 0 correspond to the firstBit of the
source. *)
PROCEDURE SetBits (VAR word : WORD;
firstBit, lastBit: CARDINAL;
pattern : WORD);
(* Masks word with pattern from firstBit to lastBit. The first
(lastBit - firstBit + 1 of pattern are used, with leading zeros
if necessary.
Examples : To set the bits to 1, the pattern 0FFFFH should be passed,
and to set the bits to 0, the pattern 0 should be passed. *)
PROCEDURE WordAnd (left, right : WORD): WORD;
(* Bitwise AND *)
PROCEDURE WordOr (left, right : WORD): WORD;
(* Bitwise OR *)
PROCEDURE WordXor (left, right : WORD): WORD;
(* Bitwise XOR *)
PROCEDURE WordNot (word : WORD): WORD;
(* Bitwise complement to 1 *)
PROCEDURE WordShr (word : WORD;
count : CARDINAL): WORD;
(* Shift Logical Right
shifts the bits in word to the right by the number of bits specified
in count. Zeros are shifted in on the left. *)
PROCEDURE WordSar (word : WORD;
count : CARDINAL): WORD;
(* Shift Arithmetic Right
shifts the bits in word to the right by the number of bits specified
in count. Bits equal to the original high order bit are shifted in
on the left, preserving the sign of the original value. *)
PROCEDURE WordShl (word : WORD;
count : CARDINAL): WORD;
(* Shift Left
shifts the bits in word to the left by the number of bits specified
in count. Zeros are shifted in on the right. *)
PROCEDURE WordRor (word : WORD;
count : CARDINAL): WORD;
(* Rotate Right
rotates word right by the number of bits specified in count *)
PROCEDURE WordRol (word : WORD;
count : CARDINAL): WORD;
(* Rotate Left
rotates word left by the number of bits specified in count *)
PROCEDURE HighByte (word : WORD): WORD;
(* Returns the high order byte value of word *)
PROCEDURE LowByte (word : WORD): WORD;
(* Returns the low order byte value of word *)
PROCEDURE Swap (VAR word : WORD);
(* Swaps the high and low order bytes value of word *)
END BitWordOps.


View File

@ -0,0 +1,52 @@
DEFINITION MODULE BlockOps;
(* Block operations.
Blocks are defined with a starting address and a size, i.e. the number
of bytes they contain.
*)
FROM SYSTEM IMPORT ADDRESS;
PROCEDURE BlockMoveForward (destination, source : ADDRESS;
size : CARDINAL);
(* Moves size bytes from source to destination, starting at the address
of source and going up until address of (source+size) is reached *)
PROCEDURE BlockMoveBackward (destination, source : ADDRESS;
size : CARDINAL);
(* Moves size bytes from source to destination, starting at (source+size)
and going down until address of source is reached *)
PROCEDURE BlockMove (destination, source : ADDRESS;
size : CARDINAL);
(* Moves size bytes from source to destination, test is made on the
addresses of source and destination to decide whether MoveBackward or
MoveForward is to be used. Note that because of this comparison,
Move is slightly slower than the two previous procedures *)
PROCEDURE BlockClear (block : ADDRESS;
size : CARDINAL);
(* Fills size bytes with 0, starting from block. *)
PROCEDURE BlockSet (block : ADDRESS;
blockSize : CARDINAL;
pattern : ADDRESS;
patternSize : CARDINAL);
(* Fills blockSize bytes starting from block with the pattern of
patternSize bytes. *)
PROCEDURE BlockEqual (block1, block2 : ADDRESS;
size : CARDINAL): BOOLEAN;
(* Returns TRUE if the blocks starting at left and right have the same
first size bytes. *)
PROCEDURE BlockPosition (block : ADDRESS;
blockSize : CARDINAL;
pattern : ADDRESS;
patternSize : CARDINAL): CARDINAL;
(* Searches pattern in block, returns the index of the first successful
match, MaxCard if no match. *)
END BlockOps.


View File

@ -0,0 +1,79 @@
(* Abbreviation: Break *)
(* Version 1.10, Nov 1984 *)
(* comments modified Feb 7, 1985 *)
DEFINITION MODULE Break;
(*
Handling of the Ctrl-Break interrupt
This module provides an interrupt handler for the
Ctrl-Break interrupt 1BH of MS-DOS and PC-DOS on the
IBM-PC. This module depends on the ROM BIOS of the
IBM-PC and will not run on any machine which is not
compatible to an IBM-PC at this level.
Module 'Break' installs a default break handler, which
stops the execution of the current program with
'System.Terminate(stopped)' when Ctrl-Break is typed.
This produces a memory dump for the stopped program.
Module 'Break' allows a program to install its own break
handler, and to enable or disable the break handler
which is currently installed.
*)
EXPORT QUALIFIED
EnableBreak, DisableBreak, InstallBreak, UnInstallBreak;
PROCEDURE EnableBreak;
(*
- Enable the activation of the current break handler
If Ctrl-Break is detected, the currently installed break
handler will be called.
*)
PROCEDURE DisableBreak;
(*
- Disable the activation of the current break handler
If a Ctrl-Break is detected, no action takes place. The
Ctrl-Break is ignored.
*)
PROCEDURE InstallBreak (BreakProc: PROC );
(*
- Install a break handler
in: BreakProc break procedure to be called upon
Crtl-Break
A program can install its own break handler. Module
'Break' maintains a stack of break procedures. The break
procedure on top of the stack (i.e. the one which was
installed most recently) will be called upon the
occurence of a ctrl-break. The default break handler
which is installed initially terminates the program with
a call to 'System.Terminate(stopped)'.
Up to four user defined break procedure may be installed
at the same time.
*)
PROCEDURE UnInstallBreak;
(*
- Uninstall the current break handler
Removes the break procedure which is currently on top of
the stack. So the last installed break procedure will be
deactivated, and the one installed previously becomes
active again.
*)
END Break.


View File

@ -0,0 +1,93 @@
DEFINITION MODULE Calendar;
(*
This module defines a Date type and operations on dates of
the Gregorian Calendar, introduced in 1582
*)
FROM DurationOps IMPORT
Duration, Unit, UnitSet;
FROM TimeDate IMPORT
Time;
TYPE Date =
RECORD
year : CARDINAL;
month : [1 .. 12];
day : [1 .. 31];
hour : [0 .. 23];
minute : [0 .. 59];
second : [0 .. 59];
thousandth: [0 .. 999];
END; (* Date *)
PROCEDURE GetMachineDate (VAR date: Date);
(* Gets the machine date *)
PROCEDURE SetMachineDate (date : Date);
(* Sets the machine date *)
PROCEDURE TimeToDate (time : Time;
VAR date : Date);
(* Type conversion from Time (in TimeDate) to Date (in Calendar) *)
PROCEDURE DateToTime (date : Date;
VAR time : Time);
(* Type conversion from Date (in Calendar) to Time (in TimeDate) *)
PROCEDURE IsValid (date : Date): BOOLEAN;
(* Returns TRUE if date is valid, according to the Gregorian calendar *)
PROCEDURE DaysIn (month : CARDINAL;
year : CARDINAL): CARDINAL;
(* Returns the number of days in the month of the year, according to
the Gregorian calendar, 0 if month is out of range. *)
PROCEDURE LeapYear (year : CARDINAL): BOOLEAN;
(* Returns TRUE if year is a leap year, according to the Gregorian
calendar (year number divisible by 400 or by 4 and not by 100) *)
PROCEDURE SameDate (date1, date2 : Date;
precision : Unit) : BOOLEAN;
(* Returns TRUE if date1 and date2 are the same date, within precision *)
PROCEDURE Later (date1, date2 : Date;
precision : Unit) : BOOLEAN;
(* Returns TRUE if date1 comes after date1, within precision *)
PROCEDURE LaterOrSameDate (date1, date2 : Date;
precision : Unit) : BOOLEAN;
(* Returns TRUE if date2 is after date1 or if date1 and date2 are the same
date, within precision *)
(* The following operations give good results only with dates following
October 15, 1582; when the Gregorian Calendar was first used.
Accuracy to the second over long periods cannot be achieved, due to
fluctuations in the Earth rotation that often cause annual corrections
of one second. *)
PROCEDURE AddToDate (date : Date;
duration : Duration;
VAR resultDate : Date);
(* Add a duration to a date, gives a new date *)
PROCEDURE SubToDate (date : Date;
duration : Duration;
VAR resultDate : Date);
(* Subtract a duration from a date, gives a new date *)
PROCEDURE DeltaDate (date1, date2 : Date;
unitFormat : UnitSet;
VAR duration : Duration);
(* Absolute value of the difference between two dates, given a duration
with units in unitFormat (see module Duration) *)
END Calendar.


View File

@ -0,0 +1,53 @@
(* Abbreviation: CardinalIO *)
(* Version 1.10, Nov 1984 *)
DEFINITION MODULE CardinalIO;
(*
Terminal input/output of CARDINALs in decimal and hex
Derived from the Lilith Modula-2 system developed by the
group of Prof. N. Wirth at ETH Zurich, Switzerland.
*)
EXPORT QUALIFIED
ReadCardinal, WriteCardinal, ReadHex, WriteHex;
PROCEDURE ReadCardinal (VAR c: CARDINAL);
(*
- Read an unsigned decimal number from the terminal.
out: c the value that was read.
The read terminates only on ESC, EOL, or blank, and the
terminator must be re-read, for example with Terminal.Read.
If the read encounters a non-digit, or a digit which would
cause the number to exceed the maximum CARDINAL value, the
bell is sounded and that character is ignored. No more
than one leading '0' is allowed.
*)
PROCEDURE WriteCardinal (c: CARDINAL; w: CARDINAL);
(*
- Write a CARDINAL in decimal format to the terminal.
in: c value to write,
w minimum field width.
The value of c is written, even if it takes more than w
digits. If it takes fewer digits, leading blanks are
output to make the field w characters wide.
*)
PROCEDURE ReadHex (VAR c: CARDINAL);
(*
- Read a CARDINAL in hexadecimal format from the terminal.
[see ReadCardinal above]
*)
PROCEDURE WriteHex (c: CARDINAL; digits: CARDINAL);
(*
- Write a CARDINAL in hexadecimal format to the terminal.
[see WriteCardinal above]
*)
END CardinalIO.


View File

@ -0,0 +1,59 @@
DEFINITION MODULE Chronometer;
(*
Management and use of 'Chrono' objects, which permits to measure times
with an estimated accuracy of 0.02 second.
All the operations on these chronos are similar to those on a real
chronometer.
*)
FROM DurationOps IMPORT
Duration, (* The measured time will be of this type *)
UnitSet; (* The units to represent the time. *)
TYPE
Chrono;
PROCEDURE NewChrono (VAR chrono : Chrono);
(* Creates a new variable of type Chrono ('Takes a chrono'), and
resets it.
A call to NewChrono is mandatory before any other operation,
otherwise the program will be HALTed at any call of such an
operation.
*)
PROCEDURE DisposeChrono (VAR chrono : Chrono);
(* Destroys variable of type Chrono ('Drops the chrono') It is
illegal to call any operation with chrono as parameter
other than NewChrono after a call to DisposeChrono *)
PROCEDURE StartChrono (chrono : Chrono);
(* Starts the chrono.
The chrono begins to measure elapsing time.
*)
PROCEDURE ReadChrono (chrono : Chrono;
format : UnitSet;
VAR elapsedTime : Duration);
(* Reads the chrono, without stopping it.
If format is empty then elapsedTime will be in seconds.
A chrono can be read several times, elapsedTime holds the
time elapsed since the last StartChrono of this chrono.
Accuracy : 0.02 second
*)
PROCEDURE StopChrono (chrono : Chrono);
(* Stops the chrono.
The time elapsing after a call to StopChrono is not taken
in account.
*)
PROCEDURE ResetChrono (chrono : Chrono);
(* Stops and Resets the chrono.
After a call to Reset the chrono is prepared to measure times from
zero. Reset is automatically called by NewChrono.
*)
END Chronometer.


View File

@ -0,0 +1,69 @@
(* Abbreviation: Conversions *)
(* Version 1.10, Nov 1984 *)
DEFINITION MODULE Conversions;
(*
Convert from INTEGER and CARDINAL to string
Derived from the Lilith Modula-2 system developed by the
group of Prof. N. Wirth at ETH Zurich, Switzerland.
*)
EXPORT QUALIFIED
ConvertOctal, ConvertHex,
ConvertCardinal, ConvertInteger, ConvertLongInt;
PROCEDURE ConvertOctal(num, len: CARDINAL;
VAR str: ARRAY OF CHAR);
(*
- Convert number to right-justified octal representation
in: num value to be represented,
len minimum width of representation,
out: str result string.
If the representation of 'num' uses fewer than 'len'
digits, blanks are added on the left. If the representa-
tion will not fit in 'str', it is truncated on the right.
*)
PROCEDURE ConvertHex(num, len: CARDINAL;
VAR str: ARRAY OF CHAR);
(*
- Convert number to right-justified hexadecimal
representation.
[see ConvertOctal]
*)
PROCEDURE ConvertCardinal(num, len: CARDINAL;
VAR str: ARRAY OF CHAR);
(*
- Convert a CARDINAL to right-justified decimal
representation.
[see ConvertOctal]
*)
PROCEDURE ConvertInteger(num: INTEGER; len: CARDINAL;
VAR str: ARRAY OF CHAR);
(*
- Convert an INTEGER to right-justified decimal
representation.
[see ConvertOctal]
Note that a leading '-' is generated if num < 0, but never
a '+'.
*)
PROCEDURE ConvertLongInt(num: LONGINT; len: CARDINAL;
VAR str: ARRAY OF CHAR);
(*
- Convert a LONGINT to right-justified decimal
representation.
[see ConvertOctal]
Note that a leading '-' is generated if num < 0, but never
a '+'.
*)
END Conversions.


View File

@ -0,0 +1,99 @@
DEFINITION MODULE DateFormat;
(*
Conversion between Date (from Calendar) and string types.
An internal format, called current format holds the template of a string,
i.e. the way in which a date is represented. Routines are provided to
change this format, as a whole or field by field.
*)
FROM Calendar IMPORT
Date;
TYPE
Format;
Order = (DateOnly, (* Select Date and/or Time, and the *)
DateAndTime, (* order in which they are represented. *)
TimeOnly,
TimeAndDate);
DayFormat = (European, (* day month year *)
US, (* month day year *)
ISO); (* year month day *)
YearFormat = (Short, (* 87 *)
Long); (* 1987 *)
MonthFormat = (InDigits, (* 03 *)
InLetters); (* March, Mars, ... *)
MonthName = ARRAY [0 .. 15] OF CHAR;
MonthList = ARRAY [1 .. 12] OF MonthName; (* Holds the months names, can *)
(* be changed by user. *)
HourFormat = (PMSec, (* 1:17:05 pm *)
PMNoSec, (* 1:17 pm *)
H24Sec, (* 13:17:05 *)
H24NoSec); (* 13:17 *)
SeparatorList = ARRAY [0 .. 5] OF CHAR; (* Holds the separators of the *)
(* different date/time compo - *)
(* components, can be changed *)
(* by the user. *)
PROCEDURE DefaultFormat (): Format;
(* Returns default date format :
dd-mmm-yyyy hh:mm:ss i.e. 13-Jun-1987 17:45:30 *)
PROCEDURE CurrentFormat (): Format;
(* Returns current date format *)
PROCEDURE SetFormat (format : Format);
(* Sets the current format to format *)
PROCEDURE SetOrder (order : Order);
(* Sets the current format's order to order.
(default: DateAndTime) *)
PROCEDURE SetDayFormat (dayformat : DayFormat);
(* Sets the current format's day format to dayFormat
(default: European *)
PROCEDURE SetYearFormat (yearFormat : YearFormat);
(* Sets the current format's year format to yearFormat
(default: Long) *)
PROCEDURE SetMonthFormat (monthFormat : MonthFormat);
(* Sets the current format's month format to monthFormat
(default: InLetters) *)
PROCEDURE SetMonthList (monthList : MonthList);
(* Sets the current format's month list to monthList
(default: Jan, Feb, Mar, Apr, May, Jun, Jul, Aug, Sep, Oct, Nov, Dec) *)
PROCEDURE SetHourFormat (hourFormat : HourFormat);
(* Sets the current format's hour format to hourFormat
(default: H24Sec) *)
PROCEDURE SetSeparator (separator : SeparatorList);
(* Sets the current format's list to separator
(default: "-- ::") *)
PROCEDURE DateToString (date : Date;
VAR image : ARRAY OF CHAR;
VAR done : BOOLEAN);
(* Converts a Date in a string of current format *)
PROCEDURE StringToDate (image : ARRAY OF CHAR;
VAR date : Date;
VAR done : BOOLEAN;
VAR errorPos : CARDINAL);
(* Converts a string in a date. The syntax of this string should be
the one defined by the current format, otherwise done is set to
FALSE and errorPos to the index of the first unexpected character
of the string. *)
END DateFormat.


View File

@ -0,0 +1,13 @@
DEFINITION MODULE DebugPMD;
(*
generates a post-mortem dump upon abnormal termination of the
application.
This module should be imported as first module in the main
module of the application to ensure correct behaviour.
Generated post-mortem dump file (.PMD) can then be used by
the PMD program to debug the application.
*)
END DebugPMD.


View File

@ -0,0 +1,10 @@
DEFINITION MODULE DebugTrace;
(*
write the procedure call chain of the application upon
abnormal termination.
*)
END DebugTrace.


View File

@ -0,0 +1,130 @@
(* Abbreviation: Decimals *)
(* Version 1.10, Dec 1984 *)
DEFINITION MODULE Decimals;
(*
Decimal Arithmetic
*)
EXPORT QUALIFIED
DECIMAL, DecDigits, DecPoint, DecSep, DecCur,
DecStatus, DecState, DecValid, StrToDec, DecToStr,
NegDec, CompareDec, AddDec, SubDec, MulDec,DivDec,
Remainder,DecRepr;
CONST
DecDigits = 18;
DecRepr = 10;
DecCur = '$';
DecPoint = '.';
DecSep = ',';
TYPE
DECIMAL = ARRAY [0..DecRepr-1] OF CHAR;
(* WARNING : Representation is
implementation dependent!
*)
DecState = (NegOvfl,
Minus,
Zero,
Plus,
PosOvfl,
Invalid
);
VAR
DecValid: BOOLEAN;
(* set after every operation *)
Remainder: CHAR;
(* remainder digit - set after DivDec *)
PROCEDURE StrToDec (String: ARRAY OF CHAR;
Picture: ARRAY OF CHAR;
VAR Dec: DECIMAL);
(*
Converts a DECIMAL number from an external format to an
internal format; after checking and matching between the
picture and the input string. The result is placed in
variable Dec.
*)
PROCEDURE DecToStr (Dec: DECIMAL;
Picture: ARRAY OF CHAR;
VAR RsltStr: ARRAY OF CHAR);
(*
Converts a DECIMAL number from an internal format to an
external format; after checking and matching between the
picture and the DECIMAL number. The result is placed in
variable RsltStr.
*)
PROCEDURE DecStatus (Dec: DECIMAL): DecState;
(*
Detects the state of the number represented as DECIMAL
and returns one of the following states :
- Negative overflow --> NegOvfl
- Negative --> Minus
- Null --> Zero
- Positive --> Plus
- Positive overflow --> PosOvfl
- Invalid representation --> Invalid
*)
PROCEDURE CompareDec (Dec0,Dec1: DECIMAL): INTEGER;
(*
Compares two DECIMAL numbers and returns an integer value
indicating the comparison result:
-1 if Dec0 is less than Dec1
0 if Dec0 equals Dec1
1 if Dec0 is greater than Dec1
*)
PROCEDURE AddDec (Dec0,Dec1: DECIMAL; VAR Sum: DECIMAL);
(*
Adds two DECIMAL numbers (Dec0 and Dec1) together and
places the result in the variable Sum.
*)
PROCEDURE SubDec (Dec0,Dec1: DECIMAL; VAR Sub: DECIMAL);
(*
Subtracts Dec1 from Dec0 and places the result in Sub.
*)
PROCEDURE MulDec (Dec0,Dec1: DECIMAL; VAR Prod: DECIMAL);
(*
Multiplies two DECIMAL numbers and places the result in
the variable Prod.
*)
PROCEDURE DivDec (Dec0,Dec1: DECIMAL; VAR Quot: DECIMAL);
(*
Dec0 is divided by Dec1. The quotient is placed in the
variable Quot and the remainder is placed in the global
variable Remainder.
*)
PROCEDURE NegDec (Dec: DECIMAL; VAR NDec: DECIMAL);
(*
The negative DECIMAL value of Dec is placed in the
variable NDec.
*)
END Decimals.


View File

@ -0,0 +1,13 @@
DEFINITION MODULE Delay;
EXPORT QUALIFIED
Delay;
PROCEDURE Delay(milliSec: INTEGER);
(*
Interrupts the program execution for approximatly 'milliSec' milliseconds.
*)
END Delay.


View File

@ -0,0 +1,179 @@
(* Abbreviation: Devices *)
(* Version 1.20, Oct 1985 *)
DEFINITION MODULE Devices;
(*
Additional facilities for device and interrupt handling
The MODULA-2/86 run-time support maintains a device mask
that indicates from which devices interrupts are enabled.
The bits of the device mask have the same meaning as the
bits in the mask register of the interrupt controller.
Module 'Devices' provides access to the device mask.
It allows a program to inquire and change the status of
a device (interrupts enabled or disabled). The device
numbers used by module 'Devices' and by the run-time
support are equal to the number of the bit in the
device mask, that indicates whether interrupts from
this device are enabled or disabled.
When a program is running at no priority, the mask
register of the interrupt controller is identical to this
device mask. When a program is running at some priority,
then the mask register of the interrupt controller is set
to the logical OR of the device mask and the corresponding
priority mask. When the priority or the device mask
changes, the MODULA-2/86 run-time support sets the
mask register of the interrupt controller accordingly.
At any point in time, all the interrupts masked out,
either in the device mask or in the current priority mask,
are disabled. The priority mask for 'no priority' does not
mask out any interrupt, i.e. its value is all zeros.
When writing interrupt handlers in MODULA-2/86, it is
strongly recommended to use only the procedures provided
by module 'Devices', and not to access directly the mask
register of the interrupt controller.
The following should be performed in order to install an
interrupt handler: First save the old interrupt vector,
then set up the interrupt handler (IOTRANSFER), and if
necessary, save the current device status (interrupts
enabled or disabled) and enable interrupts from the
device.
Before the program terminates, or in order to remove an
interrupt handler, the following sequence of procedure
calls should be performed: If necessary, restore the old
device status or disable interrupts from the device, and
then restore the old interrupt vector.
At the end of a program the MODULA-2/86 run-time support
resets the mask register of the interrupt controller to
its initial value.
In general, a call to IOTRANSFER in Modula-2 associates
a process with only the next occurence of the specified
interrupt. The procedure 'InstallHandler' provided by
module 'Devices' allows to install an interrupt handler
permanently. It associates a process, the interrupt
handler, permanently with a certain interrupt.
While it is not required to install an interrupt handler
in this way, it may be useful for handling time critical
interrupts. Installing an interrupt handler permanently
improves the performance of IOTRANSFER and of the implicit
coroutine transfer that takes place when the interrupt
occurs by about 20 percent.
'InstallHandler' must only be called after the process has
been created (by means of NEWPROCESS) and before the
process has called IOTRANSFER. For instance, it may be
called right at the beginning of the code of the process.
*)
FROM SYSTEM IMPORT ADDRESS, PROCESS;
EXPORT QUALIFIED
GetDeviceStatus, SetDeviceStatus,
SaveInterruptVector, RestoreInterruptVector,
InstallHandler, UninstallHandler;
PROCEDURE GetDeviceStatus(deviceNr: CARDINAL;
VAR enabled: BOOLEAN);
(*
- Return the status of a device in the device mask
in: deviceNr number of the device to be checked
bitnumber (0..7) of bit for device in
interrupt controller 8259 mask
out: enabled TRUE if interrupts from the device are
enabled, FALSE otherwise
*)
PROCEDURE SetDeviceStatus(deviceNr: CARDINAL;
enable: BOOLEAN);
(*
- Set the status of a device in the device mask
in: deviceNr number of the device to enable or disable
bitnumber (0..7) of bit for device in
interrupt controller 8259 mask
enable if TRUE, enable interrupts from the
device, otherwise disable them
The mask register of the interrupt controller will
be updated according to the current priority and
the new device mask.
*)
PROCEDURE SaveInterruptVector(vectorNr: CARDINAL;
VAR vector: ADDRESS);
(*
- Save the current value of an interrupt vector
in: vectorNr interrupt vector number
out: vector value of current interrupt vector
*)
PROCEDURE RestoreInterruptVector(vectorNr: CARDINAL;
vector: ADDRESS);
(*
- Restore the value of an interrupt vector
in: vectorNr interrupt vector number
vector value to restore (previously saved
with 'SaveInterruptVector')
*)
PROCEDURE InstallHandler(process: PROCESS;
vectorNr: CARDINAL);
(*
- Install an interrupt handler permanently
in: process process associated with the interrupt
handler
vectorNr interrupt vector number
The process is associated permanently to the given
interrupt vector number. This improves the performance
of IOTRANSFER and of the implicit coroutine transfer
that takes place when the interrupt occurs. A process
may be associated to at most one interrupt, and at most
one process may be associated to the same interrupt.
'InstallHandler' must only be called after the process has
been created (by means of NEWPROCESS) and before the
process has called IOTRANSFER. For instance, it may be
called right at the beginning of the code of the process.
Except for the call to 'InstallHandler', the code of a
permanently installed interrupt handler is identical to
the code of a regular interrupt handler.
*)
PROCEDURE UninstallHandler(process: PROCESS);
(*
- Uninstall an interrupt handler which has been
installed permanently
in: process process associated with the interrupt
handler
In general, there is no need to call this procedure.
The MODULA-2/86 run-time support automatically uninstalls
interrupt handlers upon termination of a (sub-)program.
*)
END Devices.


View File

@ -0,0 +1,78 @@
(* Abbreviation: Directories *)
(* Version 1.10, Nov 1984 *)
DEFINITION MODULE Directories;
(*
Additional directory operations
*)
EXPORT QUALIFIED
DirQueryProc, DirResult, DirQuery,
Delete, Rename;
TYPE
DirQueryProc = PROCEDURE(ARRAY OF CHAR, VAR BOOLEAN);
DirResult = (OK,
ExistingFile, (* rename to existing name *)
NoFile, (* file not found *)
OtherError);
PROCEDURE DirQuery( wildFileName : ARRAY OF CHAR;
DirProc : DirQueryProc;
VAR result : DirResult);
(*
- Apply the a procedure to all matching files
in: wildFileName file name, wild-characters are allowed
DirProc procedure to be called for each file
matching 'wildFileName'
out: result result of directory operation
'DirQuery' executes 'DirProc' on each file which satisfies
the specification of 'wildFileName' where wild-characters
are allowed. If no more files are found, or as soon as
'DirProc' returns FALSE, the execution is stopped.
If an incorrect filename is passed, this may return a
'result <> OK', and 'DirProc' will not be called.
Possible results are OK, NoFile, or OtherError.
*)
PROCEDURE Delete( FileName : ARRAY OF CHAR;
VAR result : DirResult);
(*
- Delete a file.
in: FileName name of the file to delete
out: result result of directory operation
Possible results are OK, or NoFile.
*)
PROCEDURE Rename( FromName : ARRAY OF CHAR;
ToName : ARRAY OF CHAR;
VAR result : DirResult);
(*
- Rename a file.
in: FromName name of the file to rename
ToName new name of the file
out: result result of directory operation
Possible results are OK, NoFile, ExistingFile, or
OtherError.
*)
END Directories.


View File

@ -0,0 +1,133 @@
(* Abbreviation: DiskDir *)
(* Version 1.10, Nov 1984 *)
(* comments modified Feb 7, 1985 *)
DEFINITION MODULE DiskDirectory;
(*
Interface to directory functions of the underlying OS
Derived from the Lilith Modula-2 system developed by the
group of Prof. N. Wirth at ETH Zurich, Switzerland.
*)
EXPORT QUALIFIED
CurrentDrive, SelectDrive,
CurrentDirectory, ChangeDirectory,
MakeDir, RemoveDir,
ResetDiskSys, ResetDrive;
PROCEDURE CurrentDrive (VAR drive: CHAR);
(*
- Returns the current default drive.
out: drive name of the default drive, given in
character format (e.g. 'A').
*)
PROCEDURE SelectDrive (drive: CHAR; VAR done: BOOLEAN);
(*
- Set default drive.
in: drive name of drive to make default, specified
in character format (e.g. 'A').
out: done TRUE if operation was successful.
The default drive will be used by all routines referring
to DK: .
*)
PROCEDURE CurrentDirectory (drive: CHAR;
VAR dir: ARRAY OF CHAR);
(*
- Gets the current directory for the specified drive.
in: drive name of the drive, specified in
character format (e.g. 'A'); blank or
0C denotes the current drive.
out: dir current directory for that drive.
Because CP/M-86 does not support named directories,
dir[0] will always be set to nul (0C) under CP/M-86.
*)
PROCEDURE ChangeDirectory (dir: ARRAY OF CHAR;
VAR done: BOOLEAN);
(*
- Set the current directory
in: dir drive and directory path name.
out: done TRUE if successful; FALSE if the
directory does not exist.
Because CP/M-86 does not support named directories,
this function has no effect and 'done' returns always
FALSE under CP/M-86.
*)
PROCEDURE MakeDir (dir: ARRAY OF CHAR;
VAR done: BOOLEAN);
(*
- Create a sub-directory
in: dir drive, optional pathname and name of
sub-directory to create.
out: done TRUE if successful; FALSE if path or
drive does not exist.
Because CP/M-86 does not support named directories,
this function has no effect and 'done' returns always
FALSE under CP/M-86.
*)
PROCEDURE RemoveDir (dir: ARRAY OF CHAR;
VAR done: BOOLEAN);
(*
- Remove a directory
in: dir drive and name of the sub-directory
to remove.
out: done: TRUE if successful; FALSE if directory
does not exist.
The specified directory must be empty, otherwise 'done'
returns FALSE and the directory is not removed.
Because CP/M-86 does not support named directories,
this function has no effect and 'done' returns always
FALSE under CP/M-86.
*)
PROCEDURE ResetDiskSys;
(*
- MS-DOS or CP/M-86 disk reset
*)
PROCEDURE ResetDrive (d: CHAR): CARDINAL;
(*
- CP/M-86 reset drive.
in: drive name of drive to make default, specified
in character format (e.g. 'A').
out: returns always zero under CP/M-86
Under DOS this function has no effect and returns always
the value 255.
*)
END DiskDirectory.


View File

@ -0,0 +1,56 @@
(* Abbreviation: DiskFiles *)
(* Version 1.10, Nov 1984 *)
(* comments modified Feb 7, 1985 *)
DEFINITION MODULE DiskFiles;
(*
Interface to disk file functions of the underlying OS.
[Private module of the MODULA-2/86 system.]
The default drive 'DK:', and drives 'A:' through 'P:'
are supported under DOS or CP/M-86. This driver provides
buffering. The maximum number of open files is 12.
Derived from the Lilith Modula-2 system developed by the
group of Prof. N. Wirth at ETH Zurich, Switzerland.
*)
FROM FileSystem IMPORT File;
EXPORT QUALIFIED
InitDiskSystem,
DiskFileProc, DiskDirProc;
PROCEDURE InitDiskSystem;
(*
- Initialize mediums for further disk file operations
This procedure has to be imported by FileSystem. This has
the side-effect, that this module is referenced and will
therefore be linked to the user program.
*)
PROCEDURE DiskFileProc (VAR f: File);
(*
- low-level interface for disk operations within a file
This procedure is passed as a parameter to the procedure
CreateMedium in FileSystem.
*)
PROCEDURE DiskDirProc (VAR f: File;
name: ARRAY OF CHAR);
(*
- low-level interface for disk operations within a
directory
This procedure is passed as a parameter to the procedure
CreateMedium in FileSystem.
*)
END DiskFiles.


View File

@ -0,0 +1,37 @@
(* Abbreviation: Display *)
(* Version 1.10, Nov 1984 *)
(* comments modified Feb 8, 1985 *)
DEFINITION MODULE Display;
(*
Low-level Console Output
[Private module of the MODULA-2/86 system]
Derived from the Lilith Modula-2 system developed by the
group of Prof. N. Wirth at ETH Zurich, Switzerland.
*)
EXPORT QUALIFIED Write;
PROCEDURE Write (ch: CHAR);
(*
- Display a character on the console.
in: ch character to be displayed.
The following codes are interpreted:
ASCII.EOL (36C) = go to beginning of next line
ASCII.ff (14C) = clear screen and set cursor home
ASCII.del (177C) = erase the last character on the left
ASCII.bs (10C) = move 1 character to the left
ASCII.cr (15C) = go to beginning of current line
ASCII.lf (12C) = move 1 line down, same column
Write uses direct console I/O.
*)
END Display.


View File

@ -0,0 +1,81 @@
(* Abbreviation: DOS3 *)
(* Version 1.20, Jun 1985 *)
DEFINITION MODULE DOS3;
(*
Additional DOS 3.0 functions
*)
FROM SYSTEM IMPORT
BYTE, WORD, ADDRESS;
EXPORT QUALIFIED
GetExtendedError,
CreateTemporaryFile,
CreateNewFile,
LockUnlockFileAccess,
GetProgramSegmentPrefix;
(* DOS 3.0 function 59H *)
PROCEDURE GetExtendedError(version: WORD;
(* BX *)
VAR extendedError: WORD;
(* AX *)
VAR errorClass: BYTE;
(* BH *)
VAR suggestedAction: BYTE;
(* BL *)
VAR locus: BYTE);
(* CH *)
(* DOS 3.0 function 5AH *)
PROCEDURE CreateTemporaryFile(path: ADDRESS;
(* DS:DX *)
attribute: WORD;
(* CX *)
VAR errorCode: WORD;
(* AX,CF *)
VAR handle: WORD;
(* AX,CF *)
VAR pathAndName: ADDRESS);
(* DS:BX *)
(* DOS 3.0 function 5BH *)
PROCEDURE CreateNewFile(pathAndName: ADDRESS;
(* DS:BX *)
attribute: WORD;
(* CX *)
VAR errorCode: WORD;
(* AX,CF *)
VAR handle: WORD);
(* AX,CF *)
(* DOS 3.0 function 5CH *)
PROCEDURE LockUnlockFileAccess(lock: BYTE;
(* AL *)
handle: WORD;
(* BX *)
offsetHigh: WORD;
(* CX *)
offsetLow: WORD;
(* DX *)
lengthHigh: WORD;
(* SI *)
lengthLow: WORD;
(* DI *)
VAR errorCode: WORD);
(* AX,CF *)
(* DOS 3.0 function 62H *)
PROCEDURE GetProgramSegmentPrefix(VAR PSPsegment: WORD);
(* BX *)
END DOS3.


View File

@ -0,0 +1,88 @@
(* Abbreviation: DOS31 *)
(* Version 1.20, Aug 1985 *)
DEFINITION MODULE DOS31;
(*
Additional DOS 3.1 functions
*)
FROM SYSTEM IMPORT
BYTE, WORD, ADDRESS;
EXPORT QUALIFIED
GetMachineName,
SetPrinterSetup,
GetPrinterSetup,
GetRedirectionListEntry,
RedirectDevice,
CancelRedirection;
(* DOS 3.1 function 5E00H *)
PROCEDURE GetMachineName(computerName: ADDRESS;
(* DS:DX *)
VAR nameNumberIndFlag: BYTE;
(* CH *)
VAR nameNumber: BYTE;
(* CL *)
VAR errorCode: WORD);
(* AX,CF *)
(* DOS 3.1 function 5E02H *)
PROCEDURE SetPrinterSetup(redirectionListIndex: WORD;
(* BX *)
setupStringLength: WORD;
(* CX *)
setupBuffer: ADDRESS;
(* DS:SI *)
VAR errorCode: WORD);
(* AX,CF *)
(* DOS 3.1 function 5E03H *)
PROCEDURE GetPrinterSetup(redirectionListIndex: WORD;
(* BX *)
setupBuffer: ADDRESS;
(* ES:DI *)
VAR setupStringLength: WORD;
(* CX *)
VAR errorCode: WORD);
(* AX,CF *)
(* DOS 3.1 function 5F02H *)
PROCEDURE GetRedirectionListEntry
(redirectionIndex: WORD;
(* BX *)
localDeviceName: ADDRESS;
(* DS:SI *)
networkName: ADDRESS;
(* ES:DI *)
VAR deviceStatusFlag: BYTE;
(* BH *)
VAR deviceType: BYTE;
(* BL *)
VAR storedParmValue: WORD;
(* CX *)
VAR errorCode: WORD);
(* AX,CF *)
(* DOS 3.1 function 5F03H *)
PROCEDURE RedirectDevice(deviceType: BYTE;
(* BL *)
valueToSaveForCaller: WORD;
(* CX *)
deviceName: ADDRESS;
(* DS:SI *)
networkPath: ADDRESS;
(* ES:DI *)
VAR errorCode: WORD);
(* AX,CF *)
(* DOS 3.1 function 5F04H *)
PROCEDURE CancelRedirection(deviceName: ADDRESS;
(* DS:SI *)
VAR errorCode: WORD);
(* AX,CF *)
END DOS31.


View File

@ -0,0 +1,11 @@
DEFINITION MODULE DosError;
(* Get the DOS error message associated to an error code. *)
PROCEDURE GetErrorMessage (errorCode : CARDINAL;
VAR errorMessage : ARRAY OF CHAR);
(* errorCode is an error number returned by DOS functions
errorMessage is at most 40 character long *)
END DosError.


View File

@ -0,0 +1,48 @@
DEFINITION MODULE DOSMemory;
(*
Interface to the DOS memory allocation routines ( DOSCALL 48H, 49H, 4AH ).
The blocks are linked to the Modula-2 RunTime Support, thus they are known
by the system and dumped in case of error.
*)
FROM SYSTEM IMPORT ADDRESS;
EXPORT QUALIFIED DOSAlloc, DOSDeAlloc, DOSAvail, DOSSetSize, DOSGetMaxSize;
PROCEDURE DOSAlloc( VAR a: ADDRESS; paraSize: CARDINAL );
(* Allocates a block of paraSize paragraphs : *)
(* a is the address of the block returned or NIL if the size *)
(* is not available or an error occured *)
PROCEDURE DOSDeAlloc( VAR a: ADDRESS; paraSize: CARDINAL );
(* DeAllocates a block previously allocated with DOSAlloc. The *)
(* paraSize passed must be the size given for allocate or setsize *)
(* a is set to the NIL value if DeAlloc succeds, not modified *)
(* an error occured. *)
(* NOTE: the address passed MUST BE the address returned by *)
(* DOSAlloc *)
PROCEDURE DOSAvail(): CARDINAL;
(* Function that returns the size ( in paragraphs ) of the largest *)
(* space available. *)
PROCEDURE DOSSetSize( a: ADDRESS; paraSize: CARDINAL; VAR errorCode: CARDINAL );
(* Sets the size of the block given to the new size given in *)
(* paraSize. The returned errorCode is : *)
(* 0 : No Error *)
(* 7 : memory control block destroyed *)
(* 8 : insufficient memory *)
(* 9 : incorrect block address *)
(* NOTE: the address passed MUST BE the address returned by *)
(* DOSAlloc *)
PROCEDURE DOSGetMaxSize( a: ADDRESS ): CARDINAL;
(* Gets the maximal paragraph size to which the block given as *)
(* parameter can be extended *)
(* NOTE: the address passed MUST BE the address returned by *)
(* DOSAlloc *)
END DOSMemory.


View File

@ -0,0 +1,81 @@
DEFINITION MODULE DurationOps;
(*
This module defines a Duration type and the relevant units.
It allows comparisons, addition and substraction on the Duration type,
and a way to do conversion between units with ease.
*)
TYPE Unit = (Millenium, Century, Year, Month,
Day, Hour, Minute, Second,
Tenth, Hundredth, Thousandth);
(* Year = mean solar time year: 365 days 5 hours 49 minutes 12 seconds
31 556 952 seconds
Month = Year / 12 : 2 629 746 seconds
*)
TYPE Duration = ARRAY Unit OF REAL;
(* Each cell of this array will hold the real amount of the relevant
unit.
*)
TYPE UnitSet = SET OF Unit;
CONST
FullUnitSet = UnitSet {Millenium, Century, Year, Month,
Day, Hour, Minute, Second,
Tenth, Hundredth, Thousandth};
EmptyUnitSet = UnitSet {};
PROCEDURE Clear (VAR duration : Duration);
(* Set duration to zero *)
PROCEDURE Format (VAR duration : Duration;
format : UnitSet);
(* Formatting of duration in format.
Allows conversions between duration units.
Unit cells of duration not in format are set to 0.0. Those in
format are set to the greatest possible 'integer' value,
except for the smallest unit which contains the remainder which may
not be integer.
If format is empty, duration is reformatted with the same units.
*)
PROCEDURE FormatOf (duration : Duration): UnitSet;
(* Returns the format of duration, i.e. the set of the non zero
unit cells.
*)
PROCEDURE Sum (left, right : Duration;
format : UnitSet;
VAR result : Duration);
(* Addition of left and right, result being formatted with format. If
format is empty then result is formatted with the union of left and
right formats
*)
PROCEDURE Diff (left, right : Duration;
format : UnitSet;
VAR result : Duration);
(* Substraction of left and right, result being formatted with format. If
format is empty then result is formatted with the union of left and
right formats
*)
PROCEDURE Equal (left, right : Duration;
accuracy : Unit) : BOOLEAN;
(* Returns TRUE if left and right are equal within accuracy *)
PROCEDURE Greater (left, right : Duration;
accuracy : Unit) : BOOLEAN;
(* Returns TRUE if left is greater than right within accuracy *)
PROCEDURE GreaterOrEqual (left, right : Duration;
accuracy : Unit) : BOOLEAN;
(* Returns TRUE if left is greater or equal than right within accuracy *)
END DurationOps.


View File

@ -0,0 +1,37 @@
(*
Title : DynMem - part of storage managing a one block heap
Creation : 87/02/19
Author : A.Richard
System : LOGITECH MODULA-2/86
Last Edit: 87.04.01
*)
DEFINITION MODULE DynMem;
(*
DynMem is used by Storage in order to manage one-block heap (16 k)
*)
FROM SYSTEM IMPORT ADDRESS;
EXPORT QUALIFIED InstallDynMem, Alloc, DeAlloc, Avail;
(* for all procedures below, the block address must be paragraph aligned *)
(* with offset 0 *)
PROCEDURE InstallDynMem( block : ADDRESS; size : CARDINAL );
(* size is the size in bytes usable by DynMem and it must be < MaxInt *)
PROCEDURE Alloc( block : ADDRESS; VAR adr : ADDRESS; size : CARDINAL );
(* adr will be the allocated block address or NIL if no space available *)
(* size is in bytes *)
PROCEDURE DeAlloc( block : ADDRESS;
VAR adr : ADDRESS; size : CARDINAL ): BOOLEAN;
(* adr return value will be NIL *)
PROCEDURE Avail( block : ADDRESS; size : CARDINAL ): BOOLEAN;
(* returns TRUE if size is available in the block *)
END DynMem.


View File

@ -0,0 +1,36 @@
(* Abbreviation: ErrorCode *)
(* Version 1.20, Jul 1985 *)
DEFINITION MODULE ErrorCode;
(*
handle return code to operating system
*)
EXPORT QUALIFIED
SetErrorCode, GetErrorCode, ExitToOS;
PROCEDURE SetErrorCode(value: CARDINAL);
(*
Sets the error return code that will be
used on normal termination; but it doesn't
terminate the program immediately.
*)
PROCEDURE GetErrorCode(VAR value: CARDINAL);
(*
Allows to inspect the set return code
*)
PROCEDURE ExitToOS;
(*
Terminate current program and return to operating
system. Set the error code corresponding to value
defined by a previous call to SetErrorCode.
implementation restriction: if the program is
using overlays, only
the current overlay will be terminated.
*)
END ErrorCode.


View File

@ -0,0 +1,51 @@
DEFINITION MODULE Exec;
(*
Shell commands. Provides a way to call the DOS interpreter, or to
execute a program from within another.
*)
FROM SYSTEM IMPORT ADDRESS;
EXPORT QUALIFIED
DosShell, DosCommand, Run, Execute;
PROCEDURE DosShell(VAR done: BOOLEAN);
(* call "COMMAND.COM" *)
(* remain in DOS command shell, until user types EXIT *)
(* finds COMMAND.COM through environment variable COMSPEC= *)
PROCEDURE DosCommand(command, parameters: ARRAY OF CHAR; VAR done: BOOLEAN);
(* call COMMAND.COM/c command parameters *)
(* execute just one DOS command and return *)
(* finds COMMAND.COM through environment variable COMSPEC= *)
(* here, the DOS shell will perform a search strategy, *)
(* using the PATH= environment variable *)
(* This call can be used to perform built in commands of *)
(* DOS (e.g. dir, ren, copy ...) *)
PROCEDURE Run(programFileName, parameters: ARRAY OF CHAR; VAR done: BOOLEAN);
(* call program with parameters *)
(* the complete filename with drive, *)
(* path and extension has to be passed. *)
(* no search strategy will be performed *)
PROCEDURE Execute(programFileNameAdr: ADDRESS;
(* pointer to program filename *)
environment: CARDINAL;
(* paragraph address of environment *)
(* 0 for current environment *)
commandLineAdr: ADDRESS;
(* pointer to command line parameters *)
(* first byte is number of characters in command line *)
(* next characters contain parameters *)
FCB1Adr, FCB2Adr: ADDRESS;
(* pointer to default file control blocks *)
VAR errorCode: CARDINAL
(* DOS error code *)
);
(* call program with given parameter block information *)
(* no search strategy will be performed *)
END Exec.


View File

@ -0,0 +1,28 @@
(* Abbreviation: FileMessage *)
(* Version 1.10, Nov 1984 *)
DEFINITION MODULE FileMessage;
(*
Write file status/response to the terminal
*)
FROM FileSystem IMPORT Response;
EXPORT QUALIFIED WriteResponse;
PROCEDURE WriteResponse (r: Response);
(*
- Write a short description of a FileSystem response on
the terminal.
in: r the response from some FileSystem
operation.
The actual argument for 'r' is typically the field 'res'
of a variable of type 'File'. The printed message is up
to 32 characters long.
*)
END FileMessage.


Some files were not shown because too many files have changed in this diff Show More