Google
 

Trailing-Edge - PDP-10 Archives - bb-h138e-bm_tops20_v6_1_distr - 6-1-sources/wfinslin.bli
There are 10 other files named wfinslin.bli in the archive. Click here to see a list.
 %TITLE 'WFINSLIN - insert a new line'
MODULE WFINSLIN (				! Insert a new line
		IDENT = '3-003'			! File: WFINSLIN.BLI Edit: CJG3003
		) =
BEGIN
!
!			  COPYRIGHT (c) 1981, 1985 BY
!	      DIGITAL EQUIPMENT CORPORATION, MAYNARD, MASS.
!		ALL RIGHTS RESERVED.
!
! THIS SOFTWARE IS FURNISHED UNDER A LICENSE AND MAY BE USED AND  COPIED
! ONLY  IN  ACCORDANCE  WITH  THE  TERMS  OF  SUCH  LICENSE AND WITH THE
! INCLUSION OF THE ABOVE COPYRIGHT NOTICE.  THIS SOFTWARE OR  ANY  OTHER
! COPIES  THEREOF MAY NOT BE PROVIDED OR OTHERWISE MADE AVAILABLE TO ANY
! OTHER PERSON.  NO TITLE TO AND OWNERSHIP OF  THE  SOFTWARE  IS  HEREBY
! TRANSFERRED.
!
! THE INFORMATION IN THIS SOFTWARE IS SUBJECT TO CHANGE  WITHOUT  NOTICE
! AND  SHOULD  NOT  BE  CONSTRUED  AS  A COMMITMENT BY DIGITAL EQUIPMENT
! CORPORATION.
!
! DIGITAL ASSUMES NO RESPONSIBILITY FOR THE USE OR  RELIABILITY  OF  ITS
! SOFTWARE ON EQUIPMENT WHICH IS NOT SUPPLIED BY DIGITAL.
!

!++
! FACILITY:	EDT -- The DEC Standard Editor
!
! ABSTRACT:
!
!	Insert a new line into the current text buffer.
!
! ENVIRONMENT:	Runs at any access mode - AST reentrant
!
! AUTHOR: Bob Kushlis, CREATION DATE: October 16, 1978
!
! MODIFIED BY:
!
! 1-001	- Original.  DJS 23-Feb-1981.  This module was created by
!	extracting routine EDT$$INS_LN  from module EDTWF.
! 1-002	- Regularize headers.  JBS 17-Mar-1981
! 1-003 - Change index for line numbers from 10 to 15.  SMB 18-Jan-1982
! 1-004 - Add line number error checks and return value.  SMB 3-Feb-1982
! 1-005	- Handle error return from splitting a bucket.  JBS 09-Jun-1982
! 1-006	- New screen update logic.  JBS 13-Sep-1982
! 1-007	- Remove EDT$$SET_WKLN.  JBS 14-Sep-1982
! 1-008 - Change the call to insert lines.  SMB 21-Sep-1982
! 1-009 - Modify to use new 48 bit macros. STS 01-Oct-1982
! 1-010 - Modify to use new compare macro. 20-Oct-1982
! 1-011	- Count inserted lines, and stop maintaining the screen data
!	   base if we have too many.  JBS 21-Oct-1982
! 1-012	- The counter also counts deleted lines.  JBS 27-Oct-1982
! 1-013 - Add parameters to SC_INSLN.  SMB 02-Dec-1982
! 1-014	- Improve code, add consistency checking.  JBS 28-Dec-1982
! 1-015 - Up the number of recs that can be inserted before SCR_REBUILD is set.  SMB 16-Feb-1983
! 1-016	- Be more defensive with select position updating.  JBS 28-Feb-1983
!
! 3-001 - Rewrite routine for Tops 10/20 to use word addressing.  GB 17-Feb-193
! 3-002 - Zero out text area before inserting new text to fix problem with
!          with bit 35 getting set when using 7 bit bytes.  GB  24-Jun-1983
! 3-003 - Modify ASSERT macro to include error code. CJG 30-Jan-1984
!--

%SBTTL 'Declarations'
!
! TABLE OF CONTENTS:
!

REQUIRE 'EDTSRC:TRAROUNAM';

FORWARD ROUTINE
    EDT$$INS_LN;

!
! INCLUDE FILES:
!

REQUIRE 'EDTSRC:EDTREQ';

!
! MACROS:
!
!	NONE
!
! EQUATED SYMBOLS:
!
!	NONE
!
! OWN STORAGE:
!
!	NONE
!
! EXTERNAL REFERENCES:
!
!	In the routine
%SBTTL 'EDT$$INS_LN  - insert a new line'

GLOBAL ROUTINE EDT$$INS_LN (			! Insert a new line
    REC_ADDR, 					! Pointer to new line
    REC_LEN					! Length of new line
    ) =

!++
! FUNCTIONAL DESCRIPTION:
!
!	Insert a new line in the text buffer.  If there is enough space in the
!	current bucket, text is moved around to make a hole and the new line is
!	inserted, otherwise, the bucket is split into two parts.
!
! FORMAL PARAMETERS:
!
!  REC_ADDR 		the address of the new line
!
!  REC_LEN 		the length of the new line
!
! IMPLICIT INPUTS:
!
!	CUR_BUF
!	WK_BUK
!	WK_CURBUK
!	WK_INSCNT
!	WK_LN
!	LNO0
!	SEL_LN
!	LN_PTR
!	RECS_INSERTED
!	SCR_LNS
!
! IMPLICIT OUTPUTS:
!
!	CUR_BUF
!	WK_LN
!	WK_BUK
!	WK_MODFD
!	WK_INSCNT
!	SEL_POS
!	RECS_INSERTED
!	SCR_REBUILD
!
! ROUTINE VALUE:
!
!	0 = insertion did not occur , 1 = successful insertion
!
! SIDE EFFECTS:
!
!	NONE
!
!--

    BEGIN

    EXTERNAL ROUTINE
	EDT$$FMT_MSG,
	EDT$$CMP_LNO,
	EDT$$WF_MAKECUR : NOVALUE,
	EDT$$WF_SPLTBUK,
	EDT$$SEL_RNGPOS,
	EDT$$SC_INSLN : NOVALUE;

    EXTERNAL
	MAX_LINES : LN_BLOCK,		! Maximum lines EDT can handle
	CUR_BUF : REF TBCB_BLOCK,	! Current text buffer control block
	WK_BUK : 			! Pointer to current bucket
	    REF BLOCK [WF_BUKT_SIZE] FIELD (WFB_FIELDS),
	WK_CURBUK,			! Number of the current bucket
	WK_INSCNT : LN_BLOCK,		! The count of inserted lines
	WK_LN : REF LIN_BLOCK,		! Pointer to current line
	WK_MODFD,			! Flag indicating bucket was modified
	LNO0 : LNOVECTOR [14],
	SEL_POS,				! Select position
	LN_PTR,				! Pointer into line buffer
	LN_BUF,				! The line buffer
	SEL_LN,				! Select line
	SCR_LNS,			! The number of text lines on the screen
	RECS_INSERTED,	! Number of records inserted and deleted since the last screen update
	SCR_REBUILD;			! 1 = the screen data structures must be rebuilt from the work file

    MESSAGES ((MAXLINVAL, INSMEM));

    LOCAL
	OLD_NEXT,
	INS_LEN;

!+
! Update the line and character counts, but first be sure we aren't exceeding
! the maximum number of lines allowed
!-

    IF (EDT$$CMP_LNO (CUR_BUF [TBCB_LINE_COUNT], MAX_LINES) GEQ 0)
    THEN
	BEGIN
	EDT$$FMT_MSG (EDT$_MAXLINVAL);
	RETURN (0);
	END;

!+
! Fix up select range if necessary.
!-

    CASE EDT$$SEL_RNGPOS () FROM -1 TO 1 OF
	SET

	[0] : 					! Current line is select line

	    IF CH$PTR_GTR (.SEL_POS, .LN_PTR)
	    THEN
		BEGIN
		IF CH$PTR_LSS (CH$PTR (LN_BUF, 0, BYTE_SIZE), CH$PLUS (.SEL_POS, -.REC_LEN))
		THEN
		    SEL_POS = CH$PTR (LN_BUF, 0, BYTE_SIZE)
		ELSE
		    SEL_POS = CH$PLUS (.SEL_POS, -.REC_LEN);

		ADDLINE (LNO0, SEL_LN, SEL_LN);
		END;

	[1] : 					! Current line is before select line
	    ADDLINE (LNO0, SEL_LN, SEL_LN);

	[-1] : 					! Current line is after select line, or no select
	    BEGIN
	    0
	    END;

	[OUTRANGE] :
	    ASSERT (8, 0);
	TES;

!+
! If we are not going to rebuild the screen data base from the work file,
! tell the screen updater that we have inserted a line.
!-

    IF ( NOT .SCR_REBUILD)
    THEN
	BEGIN
	RECS_INSERTED = .RECS_INSERTED + 1;

	IF (.RECS_INSERTED GTR (.SCR_LNS*2))
	THEN
	    SCR_REBUILD = 1
	ELSE
	    EDT$$SC_INSLN (.REC_ADDR, .REC_LEN);

	END;

!+
! Update the various counters for this text buffer.
!-
    ADDLINE (LNO0, CUR_BUF [TBCB_LINE_COUNT], CUR_BUF [TBCB_LINE_COUNT]);
    CUR_BUF [TBCB_CHAR_COUNT] = .CUR_BUF [TBCB_CHAR_COUNT] + .REC_LEN;
    ADDLINE (LNO0, CUR_BUF [TBCB_CUR_LIN], CUR_BUF [TBCB_CUR_LIN]);
    WK_LN = .WK_BUK + .CUR_BUF [TBCB_LINE_ADDR];
!+
! Compute length of line to be inserted (in words), including line no. info.
!-
    INS_LEN = ((.REC_LEN + BYTES_PER_WORD - 1) / BYTES_PER_WORD) + LIN_FIXED_SIZE + 1;
!+
! Will it fit in this bucket?
!-

    IF ((.WK_BUK [WFB_END] + .INS_LEN) GTRU WF_BUKT_SIZE)
    THEN
!+
! If we are at the beginning of a bucket and it is not the
! first bucket, then check out the previous bucket.
!-

	IF ((.CUR_BUF [TBCB_LINE_ADDR] EQL WFB_FIXED_SIZE) AND 	!
	    (.WK_BUK [WFB_PREV_BUKT] NEQ 0))
	THEN
	    BEGIN
!+
! Read the previous bucket and position to it's end.
!-
	    EDT$$WF_MAKECUR (.WK_BUK [WFB_PREV_BUKT]);
	    CUR_BUF [TBCB_LINE_ADDR] = .WK_BUK [WFB_END];
	    CUR_BUF [TBCB_CUR_BUKT] = .WK_CURBUK;
	    END;

!+
! If it still doesn't fit, then split the bucket.  Note that
! the while loop is here because it may not fit after the first
! split.  In this case the second split is guaranteed to create
! a new bucket and the line must fit.
!-

    WHILE ((.WK_BUK [WFB_END] + .INS_LEN) GTRU WF_BUKT_SIZE) DO
	BEGIN

	IF ( NOT EDT$$WF_SPLTBUK ())
	THEN
	    BEGIN
	    EDT$$FMT_MSG (EDT$_INSMEM);
	    RETURN (0);
	    END;

	END;

!+
! Make a hole for the line to be inserted.
!-
    WK_LN = .WK_BUK + .CUR_BUF [TBCB_LINE_ADDR];

    EDT$$CPY_MEM (.WK_BUK [WFB_END] - .CUR_BUF [TBCB_LINE_ADDR], .WK_LN, .WK_LN + .INS_LEN);
!+
! Update the end of bucket field to reflect new size.
!-
    WK_BUK [WFB_END] = .WK_BUK [WFB_END] + .INS_LEN;
!+
! And move the line into the bucket buffer.
!-
    WK_LN [LIN_LENGTH] = .REC_LEN;
    CH$FILL (0, .INS_LEN - (LIN_FIXED_SIZE + 1), CH$PTR (WK_LN [LIN_TEXT], 0, 36));
    CH$MOVE (.REC_LEN, .REC_ADDR, CH$PTR (WK_LN [LIN_TEXT], 0, BYTE_SIZE));
!+
! Put offset to start of this line in next word & setup offset to next line
!-
    .WK_LN + .INS_LEN - 1 = .INS_LEN;
    WK_LN [LIN_NEXT] = .INS_LEN;
!+
! Update the record pointer
!-
    CUR_BUF [TBCB_LINE_ADDR] = .CUR_BUF [TBCB_LINE_ADDR] + .INS_LEN;
!+
! Set the "modified" flag, and bump the count of inserted lines.
!
    WK_MODFD = 1;
    ADDLINE (WK_INSCNT, LNO0, WK_INSCNT);
!+
! Now make sure we are positioned correctly.
!-

    IF (.CUR_BUF [TBCB_LINE_ADDR] GEQ .WK_BUK [WFB_END])
    THEN

	IF (.WK_BUK [WFB_NEXT_BUKT] NEQ 0)
	THEN
	    BEGIN
	    EDT$$WF_MAKECUR (.WK_BUK [WFB_NEXT_BUKT]);
	    CUR_BUF [TBCB_LINE_ADDR] = WFB_FIXED_SIZE;
	    CUR_BUF [TBCB_CUR_BUKT] = .WK_CURBUK;
	    END;

    WK_LN = .WK_BUK + .CUR_BUF [TBCB_LINE_ADDR];
    RETURN (1)
    END;					! of routine EDT$$INS_LN


END
ELUDOM