DIRECTORY DragonOpsIO; CacheOps: CEDAR DEFINITIONS IMPORTS DragonOpsIO ~ BEGIN DevID: TYPE ~ DragonOpsIO.DevID; IOAddress: TYPE ~ DragonOpsIO.IOAddress; WORD: TYPE ~ DragonOpsIO.WORD; DevNum: TYPE ~ [0 .. 1024); -- Identifies uniquely a cache - equal to its DevID SetInterruptStatus: PROC [n: DevNum, itStatus: WORD] ~ INLINE { DragonOpsIO.IOWrite[Addr[n, itStatusReg], itStatus]; }; SetInterruptStatusBroadcast: PROC [itStatus: WORD] ~ INLINE { DragonOpsIO.BIOWrite[BroadcastAddr[itStatusReg], itStatus]; }; SetInterruptStatusSelf: PROC [itStatus: WORD] ~ INLINE { DragonOpsIO.IOWrite[SelfAddr[itStatusReg], itStatus]; }; ClearInterruptStatus: PROC [n: DevNum, clrMask: WORD] ~ INLINE { DragonOpsIO.IOWrite[Addr[n, itClearReg], clrMask]; }; ClearInterruptStatusBroadcast: PROC [clrMask: WORD] ~ INLINE { DragonOpsIO.BIOWrite[BroadcastAddr[itClearReg], clrMask]; }; ClearInterruptStatusSelf: PROC [clrMask: WORD] ~ INLINE { DragonOpsIO.IOWrite[SelfAddr[itClearReg], clrMask]; }; ReadInterruptStatus: PROC [n: DevNum] RETURNS [itStatus: WORD] ~ INLINE { itStatus _ DragonOpsIO.IORead[Addr[n, itStatusReg]]; }; ReadInterruptStatusSelf: PROC RETURNS [itStatus: WORD] ~ INLINE { itStatus _ DragonOpsIO.IORead[SelfAddr[itStatusReg]]; }; WriteInterruptMask: PROC [n: DevNum, itMask: WORD] ~ INLINE { DragonOpsIO.IOWrite[Addr[n, itMaskReg], itMask]; }; WriteInterruptMaskBroadcast: PROC [itMask: WORD] ~ INLINE { DragonOpsIO.BIOWrite[BroadcastAddr[itMaskReg], itMask]; }; WriteInterruptMaskSelf: PROC [itMask: WORD] ~ INLINE { DragonOpsIO.IOWrite[SelfAddr[itMaskReg], itMask]; }; ReadInterruptMask: PROC [n: DevNum] RETURNS [itMask: WORD] ~ INLINE { itMask _ DragonOpsIO.IORead[Addr[n, itMaskReg]]; }; ReadInterruptMaskSelf: PROC RETURNS [itMask: WORD] ~ INLINE { itMask _ DragonOpsIO.IORead[SelfAddr[itMaskReg]]; }; ReadID: PROC [n: DevNum] RETURNS [devID: DevID] ~ INLINE { devID _ DragonOpsIO.IORead[Addr[n, devIDReg]]; }; ReadIDSelf: PROC RETURNS [devID: DevID] ~ INLINE { devID _ DragonOpsIO.IORead[SelfAddr[devIDReg]]; }; Offset: TYPE ~ [0 .. 256); -- Offset of a register inside the cache itStatusReg: Offset = 0; -- offset to InterruptStatus - May still change itClearReg: Offset = 1; -- offset to InterruptStatus - May still change itMaskReg: Offset = 2; -- offset to InterruptMask - May still change devIDReg: Offset = 3; -- offset to InterruptMask - May still change CacheBase: WORD = 0; -- Some value to be defined later Addr: PROC [n: DevNum, offset: Offset] RETURNS [addr: IOAddress] ~ INLINE { dev: WORD _ n; addr.v _ CacheBase+1024*dev+offset; }; BroadcastAddr: PROC [offset: Offset] RETURNS [addr: IOAddress] ~ INLINE { broadcastDevNum: WORD = LAST [DevNum]; -- required by cache decoding mechanism addr.v _ CacheBase+1024*broadcastDevNum+offset; }; SelfAddr: PROC [offset: Offset] RETURNS [addr: IOAddress] ~ INLINE { addr.v _ offset; }; END. DCacheOps.mesa Copyright c 1986 by Xerox Corporation. All rights reserved. Frailong, October 13, 1986 1:48:20 pm PDT Description of cache operations from a Dragon processor. Principles Each cache has a number of I/O registers that control either its internal functions or some extension of processor functions. Cache I/O registers are usually accessible from a processor in three different ways: - Directed access: any cache may be accessed by specifying its DevNum (equal to it's DynaBus ID) - Self access: a processor may access the registers of it's own EU cache directly - Broadcast access: a processor may write a given register in all caches simultaneously I/O operations reading a register are thus available in two flavors (directed and self), whereas writes are available in three flavors (directed, self and broadcast). All functions in this package are actually inline IO instructions. Interrupt management The cache handles part of the interrupt management for the processor, coalescing multiple interrupt reasons into the single Reschedule line. The interrupt handling hardware exists both in the EU cache and in the IFU cache, but the Reschedule line of the Dragon processor is connected only to the Reschedule output of it's EU cache. Thus, the following functions are of really use only when directed to a EU cache. The interrupt management hardware in the cache consists of two registers, InterruptStatus and InterruptMask, and some related hardware. The logical function is very simple: - an interrupt reason is posted by setting a bit in InterruptStatus - interrupts are visible when they are set and that the corresponding InterruptMask bit is set - Reschedule to the processor is pulsed whenever an interrupt that was not visible before the operation becomes visible. Interrupt status management OR itStatus into InterruptStatus for the specified Cache. Reschedule will be pulsed if new interrupts are posted. pulseReschedule _ (itMask AND InterruptMask)#0 InterruptStatus _ InterruptStatus OR itStatus OR itStatus into InterruptStatus for all Caches. In each cache, pulse Reschedule if new interrupts are posted. pulseReschedule _ (itMask AND InterruptMask)#0 InterruptStatus _ InterruptStatus OR itStatus OR itStatus into InterruptStatus for the calling processor's EU Cache. Reschedule will be pulsed if new interrupts are posted. pulseReschedule _ (itMask AND InterruptMask)#0 InterruptStatus _ InterruptStatus OR itStatus Remove clrMask from InterruptStatus for the specified Cache. InterruptStatus _ InterruptStatus&~clrMask Remove clrMask from InterruptStatus for the all Caches. InterruptStatus _ InterruptStatus&~clrMask Remove clrMask from InterruptStatus for the calling processor's EU Cache. InterruptStatus _ InterruptStatus&~clrMask Return the current value of InterruptStatus for the specified Cache. itStatus _ InterruptStatus Return the current value of InterruptStatus for the calling processor's EU Cache. itStatus _ InterruptStatus Interrupt mask management Set InterruptMask for the specified Cache. If new interrupts become visible, Reschedule will be pulsed. pulseReschedule _ (itMask AND ~InterruptMask AND InterruptStatus)#0 InterruptMask _ itMask Set InterruptMask for all Caches. Each cache pulses Reschedule if new interrupts become visible. pulseReschedule _ (itMask AND ~InterruptMask AND InterruptStatus)#0 InterruptStatus _ itMask Set InterruptMask for the calling processor's EU Cache. If new interrupts become visible, Reschedule will be pulsed. pulseReschedule _ (itMask AND ~InterruptMask AND InterruptStatus)#0 InterruptStatus _ itMask Return the current value of InterruptMask for the specified Cache. itMask _ InterruptMask Return the current value of InterruptMask for the calling processor's EU Cache. itMask _ InterruptMask DynaBus ID management The cache, as all DynaBus devices, has a DynaBus identifier used in all DynaBus transactions. This identifier is also used in IO operations to identify a specific cache, as a DevNum. The bootstrap mechanis initializes the device ID for the EU and IFU caches, and guarantees that the IFU cache ID will always be exactly one more than the EU cache ID. By convention, a Dragon processor (IFU+EU+caches) is identified in software by the ID of its EU cache. This ID may be read using ReadIDSelf, thus providing processor identification for the software. Return the DynaBus device ID for the specified Cache. This function is provided only for debugging purposes, since it should return devID=n if the cache has been correctly initialized during bootstrap phase. devID _ DeviceID Return the DynaBus device ID for the calling processor's EU Cache. devID _ DeviceID Address space management Fault management Reset management Private information This information is strictly private, and figures in this interface only because INLINEs should be inthe interface if you want them to have any effect... สA˜codešœ ™ Kšœ ฯmœ1™Kšœ9˜9K˜Kšœ7™7Kšœ*™*K™K™—šกœžœ žœžœ˜9Kšœ3˜3K˜KšœI™IKšœ*™*K™K™—š กœžœ žœ žœžœ˜IKšœ4˜4K˜KšœD™DKšœ™K™K™—š กœžœžœ žœžœ˜AKšœ5˜5K˜KšœQ™QKšœ™——™šกœžœžœžœ˜=Kšœ0˜0K˜Kšœg™gKšœC™CKšœ™K™K™—šกœžœ žœžœ˜;Kšœ7˜7K˜Kšœ`™`KšœC™CKšœ™K™K™—šกœžœ žœžœ˜6Kšœ1˜1K˜Kšœt™tKšœC™CKšœ™K™K™—š กœžœ žœ žœžœ˜EKšœ0˜0K˜KšœB™BKšœ™K™K™—š กœžœžœ žœžœ˜=Kšœ1˜1K˜KšœO™OKšœ™———™Kšœค™คK™šกœžœ žœžœ˜:Kšœ.˜.K˜Kšœฯ™ฯKšœ™K™—šก œžœžœžœ˜2Kšœ/˜/K˜KšœB™BKšœ™K™——L™L™L™™K™™K™Kšœžœ7˜CK˜Kšœ /˜HKšœ /˜GKšœ -˜DKšœ -˜CK˜Kšœ žœ !˜6K˜šกœžœžœžœ˜KKšœžœ˜Kšœ#˜#K˜K˜—šก œžœžœžœ˜IKšœžœžœ  '˜NKšœ/˜/K˜K˜—šกœžœžœžœ˜DKšœ˜K˜——K˜Kšžœ˜—…— 2#ท