-- File [Ivy]<Nelson>Lupine>LupineMarshalPrivate.mesa.
-- Last edited by BZM on  9-Mar-82 17:52:16.

-- LupineMarshalPrivate is used and exported only by LupineMarshal*Impl.



DIRECTORY
  LupineManagerPrivate USING [
	ErrorCode, Nest, ParamPassingMethod, String, StringNIL],
  LupineMarshal USING [
	AllocZone, Chars, FieldInfo, ParamInfo,
	ParamLocation, ParamProcedure, ParamRecordKind,
	VariableNames, Words ],
  LupineSymbolTable USING [
	SymbolHandle, SymbolHandleNIL, TypeHandle, TypeHandleNIL, TypeInfo ],
  RPCLupine USING [maxDataLength, maxShortStringLength];


LupineMarshalPrivate: DEFINITIONS
  = BEGIN OPEN LupineManagerPrivate, LupineMarshal, ST: LupineSymbolTable;


-- Most of these constants are implicit marshaling parameters.

  MaxDataLength, MaxDataSize: Words = RPCLupine.maxDataLength;
  -- RpcPrivate.maxDataLength is the limit on DATA words in any packet.

  MaxShortStringLength: Chars = RPCLupine.maxShortStringLength;
  -- RpcPrivate.maxShortStringLength is the size limit on short string types.

  DynamicSizeThreshhold: Words = MaxDataSize;
  -- Sequences and descriptors whose net size is bigger than this
  -- are assumed to have dynamic length (they're larger than a pkt).

  MaxPointerDepth: INTEGER = 4;
  -- Random pointer recursion can go this deep before Lupine gives up;
  -- of course, LIST OF has no restrictions.

  MaxGeneratedIdLength: CARDINAL = 50;
  -- Candidate nameStrings for UniqueName should be at least this big.


-- These are information routines used between LupineMarshal*Impl.


  NeedsOperationProc: TYPE =
    PROCEDURE [type: ST.TypeHandle] RETURNS [--yes:-- BOOLEAN];

  NeedsMarshaling: NeedsOperationProc;
  ContainsRefs: NeedsOperationProc;
  ContainsEmbeddedPtrs: NeedsOperationProc;
  ContainsStatics: NeedsOperationProc;
  ContainsSequences: NeedsOperationProc;


  Cardinality: PROCEDURE [index: ST.TypeHandle] RETURNS [LONG INTEGER];

  VectorSize: PROCEDURE [vectorInfo: ST.TypeInfo] RETURNS [size: Words];

  HasDynamicIndex: PROCEDURE [vectorInfo: ST.TypeInfo]
      RETURNS [--yes:-- BOOLEAN] =
    INLINE {RETURN[VectorSize[vectorInfo] > DynamicSizeThreshhold]};

  HasEmptyIndex: PROCEDURE [index: ST.TypeHandle] RETURNS [--yes:-- BOOLEAN] =
    INLINE {RETURN[Cardinality[index] = 0]};

  IsShortString: PROCEDURE [candidate: ST.TypeHandle] RETURNS [yes: BOOLEAN];

  IsExplicitHandle: PROCEDURE [typeInfo: ST.TypeInfo] RETURNS [yes: BOOLEAN];


-- These are private routines used by LupineMarshalType*Impl.

-- Type marshaling should logically be in one module, but there's too much
-- and unpleasant module splits have resulted.


  MarshalInfo: TYPE = POINTER TO MarshalInfoObject;

  MarshalInfoObject: TYPE = RECORD [
    paramInfo: ParamInfo,
    paramFieldInfo: FieldInfo,
    varNames: VariableNames,
    direction: Direction,
    -- The following VAR fields are updated as a parameter is marshaled:
    depth, ptrDepth: LONG INTEGER ← 0,
  --transferParamIndex: ST.Index ← 0,
    numAllocs: ARRAY AllocZone OF LONG INTEGER ← ALL[0] ];

  ParentInfo: TYPE = RECORD [
    name: String ← StringNIL,
    typeInfo: ST.TypeInfo ← [info: Null[]] ];

  ParentInfoNull: ParentInfo = [];

  Direction: TYPE = {toPkt, fromPkt};

  SubStrings: TYPE = RECORD [s1, s2, s3: String ← StringNIL];

  OperationProc: TYPE = PROCEDURE [
	name: String,
	type: ST.TypeHandle,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];


-- The top-level marshaling routine:

  MarshalType: OperationProc;


-- Individual routines for marshaling type constructors:

  MarshalTransfer: PROCEDURE [
	name: String,
	transferInfo: Transfer ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalRecord: PROCEDURE [
	name: String,
	recInfo: Record ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalVariantPart: PROCEDURE [
	name: String,
	varInfo: VariantPart ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalPointer: PROCEDURE [
	name: String,
	pointerInfo: Pointer ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalRef: PROCEDURE [
	name: String,
	refInfo: Ref ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalList: PROCEDURE [
	name: String,
	listInfo: List ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalArray: PROCEDURE [
	name: String,
	arrayInfo: Array ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalDescriptor: PROCEDURE [
	name: String,
	descInfo: Descriptor ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  MarshalSequence: PROCEDURE [
	name: String,
	seqInfo: Sequence ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];


-- Utilities.

  VerifyPassingMethods: PROCEDURE [
  	var, value, result, handle, all: BOOLEAN ← FALSE,
	marshalInfo: MarshalInfo ];

  UniqueName: PROCEDURE [
	root: String,
	nameString: --VAR-- String,
	suffix: String ← StringNIL,
	marshalInfo: MarshalInfo ];

  Passing: PROCEDURE [
  	passingMethod: ParamPassingMethod,
	paramKind: ParamRecordKind,
	marshalInfo: MarshalInfo ]
      RETURNS [--yes:-- BOOLEAN] =
    INLINE BEGIN
    RETURN[
	marshalInfo.paramFieldInfo.passingMethod = passingMethod AND
	marshalInfo.paramInfo.paramRecordKind = paramKind ];
    END;



-- These are utility code generation routines used by LupineMarshalType*Impl.

  CopyOne: PROCEDURE [
	wordsNeeded: Words,
	value: SubStrings,
	nullValue, oneStmt: BOOLEAN←FALSE,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  CopyTwo: PROCEDURE [
	wordsNeeded: Words,
	value: SubStrings,
	nullValue, oneStmt: BOOLEAN←FALSE,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  CopyCharacters: PROCEDURE [
	textName: SubStrings,
	numCharsName: String,
	marshalInfo: MarshalInfo,
	nest: Nest ];

  CopyType, CopyUninterpreted: PROCEDURE [
	variableName: String,
	variableInfo: ST.TypeInfo,
	parentInfo: ParentInfo,
	marshalInfo: MarshalInfo,
	nest: Nest ];


  AllocationOperation: TYPE = {new, cons, list};

  WriteNEW: PROCEDURE [
	allocOp: AllocationOperation ← new,
	ptrInfo: ST.TypeInfo,
	marshalInfo: --VAR-- MarshalInfo ];
 

-- General marshaling utilities.   


  EnumerateOverlayParams: PROCEDURE [
	paramInfo: ParamInfo,
	overlayProc: ParamProcedure ] =
    INLINE BEGIN
    EnumerateSomeParams[paramInfo, overlayProc, inPktOverlay, inFrameAndOverlay];
    END;

  EnumerateFrameParams: PROCEDURE [
	paramInfo: ParamInfo,
	frameProc: ParamProcedure ] =
    INLINE BEGIN
    EnumerateSomeParams[paramInfo, frameProc, inFrame, inFrameAndOverlay];
    END;

  EnumerateSomeParams: PRIVATE PROCEDURE [
	paramInfo: ParamInfo, proc: ParamProcedure,
	place1, place2: ParamLocation ];



  Error: PROCEDURE [
	code: ErrorCode,
	symbol: ST.SymbolHandle ← ST.SymbolHandleNIL,
	type: ST.TypeHandle ← ST.TypeHandleNIL,
	string: String ← StringNIL,
	causeError: BOOLEAN ← TRUE ];

  Warning: PROCEDURE [
	code: ErrorCode,
	symbol: ST.SymbolHandle ← ST.SymbolHandleNIL,
	type: ST.TypeHandle ← ST.TypeHandleNIL,
	string: String ← StringNIL,
	causeError: BOOLEAN ← FALSE ];


  END.  -- LupineMarshalPrivate.