home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Media Share 9
/
MEDIASHARE_09.ISO
/
pascal
/
vdl020d.zip
/
DASDHIGH.DOC
< prev
next >
Wrap
Text File
|
1993-04-14
|
18KB
|
457 lines
(*=================== D A S D H I G H U N I T =====================
= =
= REVISION 1.0 07/16/90 J.R. TAYLOR =
= =
==========================================================================
= =
= Sequential Access Device Management Library for SDLP =
= =
= Written By Jonathan Robert Taylor =
= =
= This code is the property of columbia data products, Inc. =
= It may be distributed and used outside CDP so long as this header =
= remains intact and unmodified, and as long as it is used with a =
= licensed Standard Device Level Protocol Kernel. =
= =
= Copyright 1989,1990 Columbia Data Products =
= ALL RIGHTS RESERVED =
= =
= ---------------------------------------------------------------------- =
= Revision History Procedures changed; overall purpose of change.=
= Procedure specific revision notes below. =
= Reverse chronological order. =
= ---------------------------------------------------------------------- =
= date initials change description =
= ---------------------------------------------------------------------- =
= 12-25-90 jrt Started =
= =
==========================================================================
*)
Unit DASDHIGH;
{-------------------------------------------------------------------------}
{ Unit DASDhigh }
{-------------------------------------------------------------------------}
{ PURPOSE: This provides a simple means of addressing DASD devices and }
{ utilizing their data. All data is actually part of the Dev structure }
{ list but pointed to by the DASD device list. }
{ SOURCE: JR Taylor, Steve Lewis, Loren Grayson }
{-------------------------------------------------------------------------}
Uses
VTypes,
DOS,
VSDLPLOW,
SDLPHIGH;
Type
{--------------------------------------------------}
{ Drivelist -- a generic list for selecting drives }
{--------------------------------------------------}
DriveList = Array[1..9] of INTEGER;
{-----------------------------------------------}
{ ParInfo -- Information for a SDPS 1 partition }
{-----------------------------------------------}
ParInfo = RECORD
TypeNum : WORD;
StartBlock : LONGINT; {This is in Units of 8K bytes}
EndBlock : LONGINT;
Status : BYTE;
Reserved : WORD;
SpecVer : BYTE;
MachineType : WORD;
LocalStore : Array[0..31] of CHAR;
ExtLocalStore:Array[32..128] of BYTE;
END;
{-------------------------------------------}
{ ParTable -- An entire drive of partitions }
{-------------------------------------------}
ParTable = Array[1..32] of ParInfo;
PtrToParTable = ^ParTable;
{----------------------------------------}
{ SDPS 1 Partition Table physical layout }
{----------------------------------------}
SDPS1_PT_ENTRY=RECORD
ParType : WORD;
StartBlock : LONGINT;
EndBlock : LONGINT;
Status : BYTE;
Reserved : WORD;
SpecVer : BYTE;
MachineType : WORD;
END;
SDPS1_PT=Array[1..32] of SDPS1_PT_ENTRY;
PtrToSDPS1_PT=^SDPS1_PT;
Var
DASD : Array[1..64] of PtrToSDLPDev;
DP1 : Array[1..64] of PtrToParTable;
NumDASD : WORD;
DasdZ : INTEGER;
ParBlock : WORD;
Procedure GetPartInfo(X: INTEGER);
Procedure MakeDASDList;
Function InitSDPS_1(UnitNum : BYTE) :BYTE;
Function GetParEnd(P : POINTER) :BYTE;
Function GetEnd8K(Par : INTEGER;
P : POINTER) :LONGINT;
Function GetStart8K(Par,
ParCount : INTEGER;
Total8K : LONGINT;
P : POINTER) :LONGINT;
Function GetParSpace(Pos,Par,
ParCount : INTEGER;
Total8K : LONGINT;
VAR Start8K : LONGINT;
P : POINTER) :LONGINT;
Function CreateParEntry(Pos : INTEGER;
P : ParInfo;
TotalBytes : REAL;
UnitNum : BYTE) :WORD;
──────────────────────────────────────────────────────────────────────────────
Function GetParSpace(Pos,Par,
ParCount : INTEGER;
Total8K : LONGINT;
VAR Start8K : LONGINT;
P : POINTER) :LONGINT; {OLD}
type
ARR1024 = ARRAY[1..1024] of BYTE;
var
Datap : ^ARR1024;
Avail8K,
ST,Ed : LONGINT;
begin
Datap:=P;
if (Pos=-1) then
begin {appending}
ST:=GetEnd8K((Par-1),Datap);
ED:=Total8K;
end
else
begin {inserting}
ST:=GetEnd8K((Par-1),Datap);
ED:=GetStart8K((Par+1),ParCount,Total8K,Datap);
end;
Start8K:=ST;
{ ST:=(8192 div 512) * ST; }
{ ED:=(8192 div 512) * ED - 1;}
GetParSpace:=Ed-St;
end;
{-------------------------------------------------------------------------}
{ Function CreateParEntry }
{-------------------------------------------------------------------------}
{ IN: Pos (INTEGER) desired position (1-30) or }
{ -1 = append data to current Par Table }
{ P (ParInfo) partition information }
{ TotalBytes (REAL) total bytes available on target drive }
{ UnitNum (BYTE) target drive }
{ OUT: (WORD) action error code }
{ $00 - success, else }
{ $xx - $FE = No Table Room, }
{ $FD = Disk Space Error }
{ (NOT Avail or Allowed). }
{ $FC = Request Beyond Current Par List }
{ $FB = Position Request Error }
{ else $xx = SDLP Error/Status Code }
{ This function creates a new Partition Table Entry in the requested }
{ position. If this is not possible, the appropriate error code is }
{ returned. }
{-------------------------------------------------------------------------}
Function CreateParEntry(Pos : INTEGER;
P : ParInfo;
TotalBytes : REAL;
UnitNum : BYTE) :WORD;
type
BLine = ARRAY[0..15] of BYTE;
var
Len,
Free8K,
Total8K,
Start8K,
End8K,
PosSpace : LONGINT;
PT : BLine;
Par,
ParCount : INTEGER;
R : REAL;
Error,
Residue : BYTE;
Block : ARRAY[1..1024] of BYTE;
i : INTEGER;
begin
(*CHECK IF POSITION IN RANGE*)
if (Pos>=-1) and (Pos<31) and (Pos<>0) then
begin
Par:=Pos;
Total8K:=trunc(TotalBytes/8192);
(*GET PARTITION BLOCK*)
SDLP_Read(Unitnum,addr(Block),1,0,Error,Residue);
if (Error=$00) then
begin
ParCount:=GetParEnd(addr(Block));
(*CHECK IF PARTITION REQUEST BEYOND CURRENT TABLE*)
if ((Pos>0) and (Pos<=ParCount+1)) or (Pos=-1) then
begin
(*CHECK IF POSITION APPEND*)
If (Pos=-1) then
Par:=ParCount+1;
(*IF ROOM IN TABLE, THEN CREATE PAR ENTRY*)
if (Par<31) then
begin
(*CHECK REQUEST SIZE WITH REMAINING SPACE ON DRIVE*)
{Must make sure this is in terms of 8K Units}
Len:=(P.EndBlock - P.StartBlock) div (8192 div 512);
PosSpace:=GetParSpace(Pos,Par,ParCount,Total8K,Start8K,addr(Block));
(*AND ROLL IF WE HAVE ENOUGH SPACE TO GO*)
if (Len<=PosSpace) then
begin
End8K:=Start8k + Len;
fillchar(pt,sizeof(pt),$00);
pt[ 0]:=P.TypeNum mod 256;
pt[ 1]:=P.TypeNum div 256;
pt[ 2]:=(Start8K mod 65536) mod 256; {ST}
pt[ 3]:=(Start8K mod 65536) div 256; { }
pt[ 4]:=(Start8K div 65536) mod 256; { }
pt[ 5]:=(Start8K div 65536) div 256; {ST}
pt[ 6]:=(End8K mod 65536) mod 256; {ED}
pt[ 7]:=(End8K mod 65536) div 256; { }
pt[ 8]:=(End8K div 65536) mod 256; { }
pt[ 9]:=(End8K div 65536) div 256; {ED}
pt[10]:=P.Status;
pt[11]:=P.Reserved mod 256;
pt[12]:=P.Reserved div 256;
pt[13]:=P.SpecVer;
pt[14]:=P.MachineType mod 256;
pt[15]:=P.MachineType div 256;
SDLP_Read(UnitNum,addr(Block),1,0,Error,Residue);
if (Error=$00) then
begin
for i:=0 to 15 do
Block[((Par-1)*16)+i]:=pt[i];
SDLP_Write(UnitNum, addr(Block),1,0,Error,Residue);
end;
if (Error=$00) then
begin
SDLP_Read(UnitNum,addr(Block),1,Par,Error,Residue);
if (Error=$00) then
begin
for i:=0 to 31 do
Block[i]:=BYTE(P.LocalStore[i]);
for i:=32 to 98 do
Block[i]:=P.ExtLocalStore[i];
SDLP_Write(UnitNum,addr(Block),1,Par,Error,Residue);
end;
end;
CreateParEntry:=Error; {EITHER SUCCESS, OR READ/WRITE ERROR}
end
else
CreateParEntry:=$FD; {ILLEGAL SPACE REQUEST -NOT ENOUGH/ POS>AVAIL}
end
else
CreateParEntry:=$FE; {NO PARTITION TABLE ROOM}
end
else
CreateParEntry:=$FC; {ILLEGAL REQUEST -REQUEST BEYOND LIST}
end
else
CreateParEntry:=Error; {ERROR IN READ OPERATION}
end
else
CreateParEntry:=$FB; {POSITION REQUEST ERROR}
end;
(*========================================================================
HAD TO COMMENT THIS AREA OUT TO COMPILE
AS NONE OF THESE SEEM TO BE IMPLEMENTED YET --LG
{-------------------------------------------------------------------------}
{ Function DH_GetParMethod (INCOMPLETE) }
{-------------------------------------------------------------------------}
{ IN: DriveNum (WORD) target drive number }
{ OUT: (BYTE) partition type code (or error) }
{ $00 = unknown }
{ $01 = SDPS }
{ $02 = SDPS-2 }
{ $80 = FDISK }
{ determines what type of partitioning is being used on the target device }
{-------------------------------------------------------------------------}
Function DH_GetParMethod( DriveNum : WORD ) : BYTE;
{ returns partitioning method of the selected drive }
{ 0 = unknown, 1=sdps 1, 2=sdps2, $80 = FDISK }
{ FF= error reading drive }
{-------------------------------------------------------------------------}
{ Function DH_GetBlockNum (INCOMPLETE) }
{-------------------------------------------------------------------------}
{ IN: DriveNum (WORD) target drive number }
{ ParNum (WORD) ?? }
{ ParBlock (LONGINT) ?? }
{ OUT: (LONGINT) ?? }
{ returns logical block number for block "ParBlock" in partition "ParNum" }
{ on drive DriveNum. }
{-------------------------------------------------------------------------}
Function DH_GetBlockNum( DriveNum : WORD;
ParNum : WORD;
ParBlock : LONGINT ) : LONGINT;
{ returns logical block number for block "ParBlock" in }
{ partition "ParNum" on drive DriveNum }
{-------------------------------------------------------------------------}
{ Procedure DH_ReadPT1 (INCOMPLETE) }
{-------------------------------------------------------------------------}
{ IN: DriveNum (WORD) target drive number }
{ LSNum (WORD) Local Store Number (???) }
{ Buff (POINTER) pointer to block data buffer }
{ OUT: (none) }
{ Reads SDPS-1 Partition Table }
{-------------------------------------------------------------------------}
Procedure DH_ReadPT1( DriveNum : WORD;
LSNum : WORD;
Buff : POINTER;
Err : WORD );
{ Read SDPS1 partition table }
{-------------------------------------------------------------------------}
{ Procedure DH_WritePT1 (INCOMPLETE) }
{-------------------------------------------------------------------------}
{ IN: DriveNum (WORD) target drive number }
{ LSNum (WORD) Local Store Number (???) }
{ Buff (POINTER) pointer to block data buffer }
{ Err (WORD) error code (should be VAR!!!) }
{ OUT: (none) }
{ Write SDPS-1 Partition Table }
{-------------------------------------------------------------------------}
Procedure DH_WritePT1( DriveNum : WORD;
LSNum : WORD;
Buff : POINTER;
Err : WORD );
{ Write SDPS1 Partition Table }
{-------------------------------------------------------------------------}
{ Procedure DH_ReadLS1 (INCOMPLETE) }
{-------------------------------------------------------------------------}
{ IN: DriveNum (WORD) target drive number }
{ LSNum (WORD) Local Store number (???) }
{ Buff (POINTER) pointer to block data buffer }
{ Err (WORD) error code (should be VAR!!!) }
{ OUT: (none) }
{ Reads SDPS-1 Local Store }
{-------------------------------------------------------------------------}
Procedure DH_ReadLS1( DriveNum : WORD;
LSNum : WORD;
Buff : POINTER;
Err : WORD );
{ Read SDPS1 local store }
{-------------------------------------------------------------------------}
{ Procedure DH_WriteLS1 (INCOMPLETE) }
{-------------------------------------------------------------------------}
{ IN: DriveNum (WORD) target drive number }
{ LSNum (WORD) Local Store number (???) }
{ Buff (POINTER) pointer to block data buffer }
{ Err (WORD) error code (should be VAR!!!) }
{ OUT: (none) }
{ Writes SDPS-1 Local Store }
{-------------------------------------------------------------------------}
Procedure DH_WriteLS1( DriveNum : WORD;
LSNum : WORD;
Buff : POINTER;
Err : WORD );
{ Write SDPS1 Local Store }
*)
{-------------------------------------------------------------------------}
{ Unit DASDhigh }
{-------------------------------------------------------------------------}
BEGIN
{---------------------------}
{ init dasd list to nothing }
{---------------------------}
For DasdZ:=1 to 64 do
BEGIN
DASD[DasdZ]:=NIL;
DP1[DasdZ]:=NIL;
END;
ParBlock := 0;
END.