From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.9 required=5.0 tests=BAYES_00 autolearn=unavailable autolearn_force=no version=3.4.4 Path: eternal-september.org!reader01.eternal-september.org!reader02.eternal-september.org!news.eternal-september.org!mx02.eternal-september.org!.POSTED!not-for-mail From: Simon Wright Newsgroups: comp.lang.ada Subject: Re: Protected Objects and Interrupt Handlers Date: Thu, 25 Feb 2016 15:59:46 +0000 Organization: A noiseless patient Spider Message-ID: References: <7663896a-a15e-47fd-8c7e-54a1c20d8d0f@googlegroups.com> <2922ffdd-9678-4502-9bcb-8b199af91543@googlegroups.com> Mime-Version: 1.0 Content-Type: text/plain Injection-Info: mx02.eternal-september.org; posting-host="03d977edd803a9f1bf346d48fa393156"; logging-data="2748"; mail-complaints-to="abuse@eternal-september.org"; posting-account="U2FsdGVkX19STqsty1obhtymRIMNVtMIDuYOjLHpGr8=" User-Agent: Gnus/5.13 (Gnus v5.13) Emacs/24.5 (darwin) Cancel-Lock: sha1:7XcnlNy7UlSVQPtSVBOpaJ//gfs= sha1:IwsBTZtUmo0nBpRsDEfPVzoyPgo= Xref: news.eternal-september.org comp.lang.ada:29605 Date: 2016-02-25T15:59:46+00:00 List-Id: Maciej Sobczak writes: > Note also that it is easy to combine these two approaches - just let > the interrupt handler (a procedure) interact with a dedicated > protected object (by forwarding to its procedures) as if it was a > regular work-item producing task - which, conceptually, it really is. I think this approach might have problems; if the PO doesn't expect to be called in an interrupt context, it may do things (like block) which an ISR should never do. The AdaCore sfp RTS (the 2014 version, anyway) says (comments removed) procedure Lock (Object : Protection_Access) is Self_Id : constant Task_Id := Self; Caller_Priority : constant Any_Priority := Get_Priority (Self_Id); begin if Object.Owner = Self_Id then raise Program_Error; end if; if Caller_Priority > Object.Ceiling then raise Program_Error; end if; Set_Priority (Self_Id, Object.Ceiling); if Multiprocessor then Multiprocessors.Fair_Locks.Lock (Object.Lock); end if; Object.Owner := Self_Id; Object.Caller_Priority := Caller_Priority; Self_Id.Common.Protected_Action_Nesting := Self_Id.Common.Protected_Action_Nesting + 1; end Lock; where the *_Id references are to the currently running task, which of course has no relationship to the current ISR. (I have to say that, given that Lock is called in interrupt contexts (I just checked with the debugger) I don't see how this works at all! Perhaps GNAT detects AdaCore's RTS and generates different code? Also, the 2015 version of Lock is the same)