DataMuseum.dk

Presents historical artifacts from the history of:

Rational R1000/400

This is an automatic "excavation" of a thematic subset of
artifacts from Datamuseum.dk's BitArchive.

See our Wiki for more about Rational R1000/400

Excavated with: AutoArchaeologist - Free & Open Source Software.


top - download

⟦96c2b69ec⟧ Ada Source

    Length: 8192 (0x2000)
    Types: Ada Source
    Notes: 03_class, FILE, R1k_Segment, e3_tag, package body First_Task, seg_05828f

Derivation

└─⟦8527c1e9b⟧ Bits:30000544 8mm tape, Rational 1000, Arrival backup of disks in PAM's R1000
    └─ ⟦cfc2e13cd⟧ »Space Info Vol 2« 
        └─⟦this⟧ 

E3 Source Code



with System;
with Screen_Io;
use Screen_Io;
package body First_Task is
    subtype Same_Ex is Ex;

    task Census is
        -- keeps track of the number of active exploring tasks.
        entry Update (Del : Integer);
    end Census;

    task body Census is
        Population : Integer := 1;
    begin
        loop
            select
                accept Update (Del : Integer) do
                    Population := Population + Del;
                    Putsn ("active tasks: ", Population, 1, 1);
                end Update;
            or
                terminate;
            end select;
        end loop;
    end Census;

    task body Ex is
        -- A new exploring task is created whenever an active exploring task
        -- finds an unexplored cell to the right or left of its current pos.
        -- Each such task has a pointer to itself and to its parent. When it
        -- reaches a dead end, it waits for a report from each son, and then
        -- reports in turn to its parent. The first task to read the goal re-
        -- ports success to its parent, and the successful path is retraced.


        Pos, New_Pos, Start_Pos : Position;
        Dir : Direction;
        Found : Boolean := False;
        Self, Pop : Explore;
        Progeny : Integer := 0;

        procedure Try_Turn (New_Dir : Direction) is
            -- see if path exists to right or left of current position.
            New_Pos : Position := Next_Pos (Pos, New_Dir);
            Son : Explore;
        begin
            if Open (New_Pos) then
                -- This test and the corresponding spawn should be a critical
                -- section. As it stands, the program is clearly erroneous,
                -- as  the shared variable -dist-  is being accessed
                -- without explicit synchronization.
                --  The algorithm works in any case, and the benign rare
                -- condition here is left to allow for greater parallelism,
                --  at the possible expense of additional (short-lived
                -- and superflouous) tasks.

                Son := new Same_Ex;
                Progeny := Progeny + 1;
                Census.Update (1);
                Son.Start (Pos, New_Dir, Son, Self);
            end if;
        end Try_Turn;

        procedure Retrace (There, Here : Position) is
            -- mark the path to success, in reverse.
            Bck : Direction := Back_Of (Dir);
            Pos : Position := There;
            Ch : Character;
        begin
            -- case System.System_Name is
            -- when System.Pc_Dos =>
            --         Ch := Ascii.Eot;
            --     when others =>
            Ch := '+';
            --  end case;
            while Pos /= Here loop
                Putcb (Ch, Pos.Row, Pos.Col);
                Pos := Next_Pos (Pos, Bck);
            end loop;
        end Retrace;

    begin
        -- upon creation, get identity from creator, and current location.
        accept Start (P : Position; D : Direction; Me, Parent : Explore) do
            Start_Pos := P;
            Pos := Next_Pos (P, D);
            Dir := D;
            Self := Me;
            Pop := Parent;
        end Start;

        Putc ('O', Pos.Row, Pos.Col);           -- hatch.
        Putc ('o', Pos.Row, Pos.Col);

        begin
            loop
                Mark (Pos, Dir);
                Dist (Pos.Row, Pos.Col) := 0;           -- we've been here.
                Try_Turn (Right_Of (Dir));               -- look both ways.
                Try_Turn (Left_Of (Dir));
                New_Pos := Next_Pos (Pos, Dir); -- and proceed.
                exit when New_Pos = Goal or not Open (New_Pos);
                Pos := New_Pos;
            end loop;
        exception
            when Storage_Error | Program_Error =>
                Puts ("unable to create new tasks. Try simpler maze.", 23, 1);
        end;

        if New_Pos = Goal then
            Putc (Ascii.Bel, Goal.Row, Goal.Col);        -- bingo!
            Found := True;
        else
            for I in 1 .. Progeny loop            -- anyone got there?
                accept Report (Success : Boolean; Where : Position) do
                    Found := Success;
                    Pos := Where;
                end Report;
                exit when Found;
            end loop;
        end if;
        if Found then
            Retrace (Pos, Start_Pos);
        end if;
        if Pop /= Self then                     -- not true for first task.
            if Pop'Callable then
                Pop.Report (Found, Start_Pos);
            end if;
        elsif not Found then
            Puts ("no  way from here to there      ", 23, 1);
        end if;

        Census.Update (-1);                     -- exit discretely.
    end Ex;

end First_Task;

E3 Meta Data

    nblk1=7
    nid=0
    hdr6=e
        [0x00] rec0=20 rec1=00 rec2=01 rec3=08e
        [0x01] rec0=16 rec1=00 rec2=06 rec3=04a
        [0x02] rec0=1b rec1=00 rec2=05 rec3=028
        [0x03] rec0=01 rec1=00 rec2=07 rec3=000
        [0x04] rec0=1a rec1=00 rec2=04 rec3=058
        [0x05] rec0=1e rec1=00 rec2=03 rec3=000
        [0x06] rec0=01 rec1=00 rec2=02 rec3=000
    tail 0x217658c2487e282f0e959 0x42a00088462060003