prio/Paper/Paper.thy
changeset 321 6a4249608ad0
parent 320 630754a81bdb
child 322 c37b387110d0
equal deleted inserted replaced
320:630754a81bdb 321:6a4249608ad0
   895   attractive (especially in light of the flawed proof by Sha et
   895   attractive (especially in light of the flawed proof by Sha et
   896   al.~\cite{Sha90}), we found that the formalisation can even help us
   896   al.~\cite{Sha90}), we found that the formalisation can even help us
   897   with efficiently implementing PIP.
   897   with efficiently implementing PIP.
   898 
   898 
   899   For example Baker complained that calculating the current precedence
   899   For example Baker complained that calculating the current precedence
   900   in PIP is quite ``heavy weight'' in Linux (see our Introduction).
   900   in PIP is quite ``heavy weight'' in Linux (see the Introduction).
   901   In our model of PIP the current precedence of a thread in a state s
   901   In our model of PIP the current precedence of a thread in a state s
   902   depends on all its dependants---a ``global'' transitive notion,
   902   depends on all its dependants---a ``global'' transitive notion,
   903   which is indeed heavy weight (see Def.~shown in \eqref{cpreced}).
   903   which is indeed heavy weight (see Def.~shown in \eqref{cpreced}).
   904   We can however prove how to improve upon this. For this let us
   904   We can however improve upon this. For this let us define the notion
   905   define the notion of @{term children} of a thread as
   905   of @{term children} of a thread @{text th} in a state @{text s} as
   906 
   906 
   907   \begin{isabelle}\ \ \ \ \ %%%
   907   \begin{isabelle}\ \ \ \ \ %%%
   908   \begin{tabular}{@ {}l}
   908   \begin{tabular}{@ {}l}
   909   @{thm children_def2}
   909   @{thm children_def2}
   910   \end{tabular}
   910   \end{tabular}
   911   \end{isabelle}
   911   \end{isabelle}
   912 
   912 
   913   \noindent
   913   \noindent
   914   where a child is a thread that is one ``hop'' away in the @{term RAG} from the 
   914   where a child is a thread that is one ``hop'' away from the tread
   915   tread @{text th} (and waiting for @{text th} to release a resource). We can prove that
   915   @{text th} in the @{term RAG} (and waiting for @{text th} to release
       
   916   a resource). We can prove that
   916 
   917 
   917   \begin{lemma}\label{childrenlem}
   918   \begin{lemma}\label{childrenlem}
   918   @{text "If"} @{thm (prem 1) cp_rec} @{text "then"}
   919   @{text "If"} @{thm (prem 1) cp_rec} @{text "then"}
   919   \begin{center}
   920   \begin{center}
   920   @{thm (concl) cp_rec}.
   921   @{thm (concl) cp_rec}.
   923   
   924   
   924   \noindent
   925   \noindent
   925   That means the current precedence of a thread @{text th} can be
   926   That means the current precedence of a thread @{text th} can be
   926   computed locally by considering only the children of @{text th}. In
   927   computed locally by considering only the children of @{text th}. In
   927   effect, it only needs to be recomputed for @{text th} when one of
   928   effect, it only needs to be recomputed for @{text th} when one of
   928   its children change their current precedence.  Once the current 
   929   its children changes its current precedence.  Once the current 
   929   precedence is computed in this more efficient manner, the selection
   930   precedence is computed in this more efficient manner, the selection
   930   of the thread with highest precedence from a set of ready threads is
   931   of the thread with highest precedence from a set of ready threads is
   931   a standard scheduling operation implemented in most operating
   932   a standard scheduling operation implemented in most operating
   932   systems.
   933   systems.
   933 
   934 
   934   Of course the main implementation work for PIP involves the scheduler
   935   Of course the main implementation work for PIP involves the
   935   and coding how it should react to the events, for example which 
   936   scheduler and coding how it should react to events.  Below we
   936   datastructures need to be modified (mainly @{text RAG} and @{text cprec}).
   937   outline how our formalisation guides this implementation for each
   937   Below we outline how our formalisation guides this implementation for each 
   938   kind of event.\smallskip
   938   event.\smallskip
       
   939 *}
   939 *}
   940 
   940 
   941 (*<*)
   941 (*<*)
   942 context step_create_cps
   942 context step_create_cps
   943 begin
   943 begin
   944 (*>*)
   944 (*>*)
   945 text {*
   945 text {*
   946   \noindent
   946   \noindent
   947   @{term "Create th prio"}: We assume that the current state @{text s'} and 
   947   \colorbox{mygrey}{@{term "Create th prio"}:} We assume that the current state @{text s'} and 
   948   the next state @{term "s \<equiv> Create th prio#s'"} are both valid (meaning the event
   948   the next state @{term "s \<equiv> Create th prio#s'"} are both valid (meaning the event
   949   is allowed to occur). In this situation we can show that
   949   is allowed to occur). In this situation we can show that
   950 
   950 
   951   \begin{isabelle}\ \ \ \ \ %%%
   951   \begin{isabelle}\ \ \ \ \ %%%
   952   \begin{tabular}{@ {}l}
   952   \begin{tabular}{@ {}l}
   953   @{thm eq_dep}\\
   953   @{thm eq_dep},\\
   954   @{thm eq_cp_th}\\
   954   @{thm eq_cp_th}, and\\
   955   @{thm[mode=IfThen] eq_cp}
   955   @{thm[mode=IfThen] eq_cp}
   956   \end{tabular}
   956   \end{tabular}
   957   \end{isabelle}
   957   \end{isabelle}
   958 
   958 
   959   \noindent
   959   \noindent
   960   This means we do not have recalculate the @{text RAG} and also none of the
   960   This means we do not have recalculate the @{text RAG} and also none of the
   961   current precedences of the other threads. The current precedence of the created
   961   current precedences of the other threads. The current precedence of the created
   962   thread is just its precedence, that is the pair @{term "(prio, length (s::event list))"}.
   962   thread @{text th} is just its precedence, namely the pair @{term "(prio, length (s::event list))"}.
   963   \smallskip
   963   \smallskip
   964   *}
   964   *}
   965 (*<*)
   965 (*<*)
   966 end
   966 end
   967 context step_exit_cps
   967 context step_exit_cps
   968 begin
   968 begin
   969 (*>*)
   969 (*>*)
   970 text {*
   970 text {*
   971   \noindent
   971   \noindent
   972   @{term "Exit th"}: We again assume that the current state @{text s'} and 
   972   \colorbox{mygrey}{@{term "Exit th"}:} We again assume that the current state @{text s'} and 
   973   the next state @{term "s \<equiv> Exit th#s'"} are both valid. We can show that
   973   the next state @{term "s \<equiv> Exit th#s'"} are both valid. We can show that
   974 
   974 
   975   \begin{isabelle}\ \ \ \ \ %%%
   975   \begin{isabelle}\ \ \ \ \ %%%
   976   \begin{tabular}{@ {}l}
   976   \begin{tabular}{@ {}l}
   977   @{thm eq_dep}\\
   977   @{thm eq_dep}, and\\
   978   @{thm[mode=IfThen] eq_cp}
   978   @{thm[mode=IfThen] eq_cp}
   979   \end{tabular}
   979   \end{tabular}
   980   \end{isabelle}
   980   \end{isabelle}
   981 
   981 
   982   \noindent
   982   \noindent
   983   This means also we do not have to recalculate the @{text RAG} and
   983   This means again we do not have to recalculate the @{text RAG} and
   984   not the current precedences for the other threads. Since @{term th} is not
   984   also not the current precedences for the other threads. Since @{term th} is not
   985   alive anymore in state @{term "s"}, there is no need to calculate its
   985   alive anymore in state @{term "s"}, there is no need to calculate its
   986   current precedence.
   986   current precedence.
   987   \smallskip
   987   \smallskip
   988 *}
   988 *}
   989 (*<*)
   989 (*<*)
   991 context step_set_cps
   991 context step_set_cps
   992 begin
   992 begin
   993 (*>*)
   993 (*>*)
   994 text {*
   994 text {*
   995   \noindent
   995   \noindent
   996   @{term "Set th prio"}: We assume that @{text s'} and 
   996   \colorbox{mygrey}{@{term "Set th prio"}:} We assume that @{text s'} and 
   997   @{term "s \<equiv> Set th prio#s'"} are both valid. We can show that
   997   @{term "s \<equiv> Set th prio#s'"} are both valid. We can show that
   998 
   998 
   999   \begin{isabelle}\ \ \ \ \ %%%
   999   \begin{isabelle}\ \ \ \ \ %%%
  1000   \begin{tabular}{@ {}l}
  1000   \begin{tabular}{@ {}l}
  1001   @{thm[mode=IfThen] eq_dep}\\
  1001   @{thm[mode=IfThen] eq_dep}, and\\
  1002   @{thm[mode=IfThen] eq_cp}
  1002   @{thm[mode=IfThen] eq_cp}
  1003   \end{tabular}
  1003   \end{tabular}
  1004   \end{isabelle}
  1004   \end{isabelle}
  1005 
  1005 
  1006   \noindent
  1006   \noindent
  1007   The first is again telling us we do not need to change the @{text RAG}. The second
  1007   The first property is again telling us we do not need to change the @{text RAG}. The second
  1008   however states that only threads that are \emph{not} dependent on @{text th} have their
  1008   however states that only threads that are \emph{not} dependants of @{text th} have their
  1009   current precedence unchanged. For the others we have to recalculate the current
  1009   current precedence unchanged. For the others we have to recalculate the current
  1010   precedence. To do this we can start from @{term "th"} 
  1010   precedence. To do this we can start from @{term "th"} 
  1011   and follow the @{term "depend"}-chains to recompute the @{term "cp"} of every 
  1011   and follow the @{term "depend"}-chains to recompute the @{term "cp"} of every 
  1012   thread encountered on the way using Lemma~\ref{childrenlem}. Since the @{term "depend"}
  1012   thread encountered on the way using Lemma~\ref{childrenlem}. Since the @{term "depend"}
  1013   is loop free, this procedure always stop. The the following two lemmas show this 
  1013   is loop free, this procedure will always stop. The following two lemmas show, however, 
  1014   procedure can actually stop often earlier.
  1014   that this procedure can actually stop often earlier without having to consider all
       
  1015   dependants.
  1015 
  1016 
  1016   \begin{isabelle}\ \ \ \ \ %%%
  1017   \begin{isabelle}\ \ \ \ \ %%%
  1017   \begin{tabular}{@ {}l}
  1018   \begin{tabular}{@ {}l}
  1018   @{thm[mode=IfThen] eq_up_self}\\
  1019   @{thm[mode=IfThen] eq_up_self}\\
  1019   @{text "If"} @{thm (prem 1) eq_up}, @{thm (prem 2) eq_up} and @{thm (prem 3) eq_up}\\
  1020   @{text "If"} @{thm (prem 1) eq_up}, @{thm (prem 2) eq_up} and @{thm (prem 3) eq_up}\\
  1027   The second states that if an intermediate @{term cp}-value does not change, then
  1028   The second states that if an intermediate @{term cp}-value does not change, then
  1028   the procedure can also stop, because none of its dependent threads will
  1029   the procedure can also stop, because none of its dependent threads will
  1029   have their current precedence changed.
  1030   have their current precedence changed.
  1030   \smallskip
  1031   \smallskip
  1031   *}
  1032   *}
  1032 
       
  1033 (*<*)
  1033 (*<*)
  1034 end
  1034 end
  1035 context step_v_cps_nt
  1035 context step_v_cps_nt
  1036 begin
  1036 begin
  1037 (*>*)
  1037 (*>*)
  1038 text {*
  1038 text {*
  1039   \noindent
  1039   \noindent
  1040   @{term "V th cs"}: We assume that @{text s'} and 
  1040   \colorbox{mygrey}{@{term "V th cs"}:} We assume that @{text s'} and 
  1041   @{term "s \<equiv> V th cs#s'"} are both valid. We have to consider two
  1041   @{term "s \<equiv> V th cs#s'"} are both valid. We have to consider two
  1042   subcases: one where there is a thread to ``take over'' the released
  1042   subcases: one where there is a thread to ``take over'' the released
  1043   resource @{text cs}, and where there is not. Let us consider them
  1043   resource @{text cs}, and one where there is not. Let us consider them
  1044   in turn. Suppose in state @{text s}, the thread @{text th'} takes over
  1044   in turn. Suppose in state @{text s}, the thread @{text th'} takes over
  1045   resource @{text cs} from thread @{text th}. We can show
  1045   resource @{text cs} from thread @{text th}. We can show
  1046 
  1046 
  1047 
  1047 
  1048   \begin{isabelle}\ \ \ \ \ %%%
  1048   \begin{isabelle}\ \ \ \ \ %%%
  1063   For @{text th} and @{text th'} we need to use Lemma~\ref{childrenlem} to
  1063   For @{text th} and @{text th'} we need to use Lemma~\ref{childrenlem} to
  1064   recalculate their current prcedence since their children have changed. *}(*<*)end context step_v_cps_nnt begin (*>*)text {*
  1064   recalculate their current prcedence since their children have changed. *}(*<*)end context step_v_cps_nnt begin (*>*)text {*
  1065   \noindent
  1065   \noindent
  1066   In the other case where there is no thread that takes over @{text cs}, we can show how
  1066   In the other case where there is no thread that takes over @{text cs}, we can show how
  1067   to recalculate the @{text RAG} and also show that no current precedence needs
  1067   to recalculate the @{text RAG} and also show that no current precedence needs
  1068   to be recalculated, except for @{text th} (like in the case above).
  1068   to be recalculated.
  1069 
  1069 
  1070   \begin{isabelle}\ \ \ \ \ %%%
  1070   \begin{isabelle}\ \ \ \ \ %%%
  1071   \begin{tabular}{@ {}l}
  1071   \begin{tabular}{@ {}l}
  1072   @{thm depend_s}\\
  1072   @{thm depend_s}\\
  1073   @{thm eq_cp}
  1073   @{thm eq_cp}
  1080 begin
  1080 begin
  1081 (*>*)
  1081 (*>*)
  1082 
  1082 
  1083 text {*
  1083 text {*
  1084   \noindent
  1084   \noindent
  1085   @{term "P th cs"}: We assume that @{text s'} and 
  1085   \colorbox{mygrey}{@{term "P th cs"}:} We assume that @{text s'} and 
  1086   @{term "s \<equiv> P th cs#s'"} are both valid. We again have to analyse two subcases, namely
  1086   @{term "s \<equiv> P th cs#s'"} are both valid. We again have to analyse two subcases, namely
  1087   the one where @{text cs} is locked, and where it is not. We treat the second case
  1087   the one where @{text cs} is locked, and where it is not. We treat the second case
  1088   first by showing that
  1088   first by showing that
  1089   
  1089   
  1090   \begin{isabelle}\ \ \ \ \ %%%
  1090   \begin{isabelle}\ \ \ \ \ %%%
  1094   \end{tabular}
  1094   \end{tabular}
  1095   \end{isabelle}
  1095   \end{isabelle}
  1096 
  1096 
  1097   \noindent
  1097   \noindent
  1098   This means we do not need to add a holding edge to the @{text RAG} and no
  1098   This means we do not need to add a holding edge to the @{text RAG} and no
  1099   current precedence must be recalculated (including that for @{text th}).*}(*<*)end context step_P_cps_ne begin(*>*) text {*
  1099   current precedence needs to be recalculated.*}(*<*)end context step_P_cps_ne begin(*>*) text {*
  1100   \noindent
  1100   \noindent
  1101   In the second case we know that resouce @{text cs} is locked. We can show that
  1101   In the second case we know that resouce @{text cs} is locked. We can show that
  1102   
  1102   
  1103   \begin{isabelle}\ \ \ \ \ %%%
  1103   \begin{isabelle}\ \ \ \ \ %%%
  1104   \begin{tabular}{@ {}l}
  1104   \begin{tabular}{@ {}l}
  1107   \end{tabular}
  1107   \end{tabular}
  1108   \end{isabelle}
  1108   \end{isabelle}
  1109 
  1109 
  1110   \noindent
  1110   \noindent
  1111   That means we have to add a waiting edge to the @{text RAG}. Furthermore
  1111   That means we have to add a waiting edge to the @{text RAG}. Furthermore
  1112   the current precedence for all threads that are not dependent on @{text th}
  1112   the current precedence for all threads that are not dependants of @{text th}
  1113   are unchanged. For the others we need to follow the @{term "depend"}-chains 
  1113   are unchanged. For the others we need to follow the edges 
  1114   in the @{text RAG} and recompute the @{term "cp"}. However, like in the 
  1114   in the @{text RAG} and recompute the @{term "cp"}. However, like in the 
  1115   @{text Set}-event, this operation can stop often earlier, namely when intermediate
  1115   @case of {text Set}, this operation can stop often earlier, namely when intermediate
  1116   values do not change.
  1116   values do not change.
  1117   *}
  1117   *}
  1118 (*<*)
  1118 (*<*)
  1119 end
  1119 end
  1120 (*>*)
  1120 (*>*)
  1121 
       
  1122 text {*
  1121 text {*
  1123   \noindent
  1122   \noindent
  1124   TO DO a few sentences summarising what has been achieved.
  1123   A pleasing result of our formalisation is that the properties in
       
  1124   this section closely inform an implementation of PIP:  Whether the
       
  1125   @{text RAG} needs to be reconfigured or current precedences need to
       
  1126   recalculated for an event is given by a lemma we proved.
  1125 *}
  1127 *}
  1126 
  1128 
  1127 section {* Conclusion *}
  1129 section {* Conclusion *}
  1128 
  1130 
  1129 text {* 
  1131 text {* 
  1139   that a mechanically checked proof avoids the flaws that crept into their
  1141   that a mechanically checked proof avoids the flaws that crept into their
  1140   informal reasoning. We achieved this goal: The correctness of PIP now
  1142   informal reasoning. We achieved this goal: The correctness of PIP now
  1141   only hinges on the assumptions behind our formal model. The reasoning, which is
  1143   only hinges on the assumptions behind our formal model. The reasoning, which is
  1142   sometimes quite intricate and tedious, has been checked beyond any
  1144   sometimes quite intricate and tedious, has been checked beyond any
  1143   reasonable doubt by Isabelle/HOL. We can also confirm that Paulson's
  1145   reasonable doubt by Isabelle/HOL. We can also confirm that Paulson's
  1144   inductive method to protocol verification~\cite{Paulson98} is quite
  1146   inductive method for protocol verification~\cite{Paulson98} is quite
  1145   suitable for our formal model and proof. The traditional application
  1147   suitable for our formal model and proof. The traditional application
  1146   area of this method is security protocols.  The only other
  1148   area of this method is security protocols.  The only other
  1147   application of Paulson's method we know of outside this area is
  1149   application of Paulson's method we know of outside this area is
  1148   \cite{Wang09}.
  1150   \cite{Wang09}.
  1149 
  1151 
  1167 
  1169 
  1168   PIP is a scheduling algorithm for single-processor systems. We are
  1170   PIP is a scheduling algorithm for single-processor systems. We are
  1169   now living in a multi-processor world. So the question naturally
  1171   now living in a multi-processor world. So the question naturally
  1170   arises whether PIP has any relevance in such a world beyond
  1172   arises whether PIP has any relevance in such a world beyond
  1171   teaching. Priority Inversion certainly occurs also in
  1173   teaching. Priority Inversion certainly occurs also in
  1172   multi-processor systems.  However, the surprising answer, according to
  1174   multi-processor systems.  However, the surprising answer, according
  1173   \cite{Steinberg10}, is that except for one unsatisfactory proposal
  1175   to \cite{Steinberg10}, is that except for one unsatisfactory
  1174   nobody has a good idea for how PIP should be modified to work
  1176   proposal nobody has a good idea for how PIP should be modified to
  1175   correctly on multi-processor systems. The difficulties become clear
  1177   work correctly on multi-processor systems. The difficulties become
  1176   when considering that locking and releasing a resource always
  1178   clear when considering that locking and releasing a resource always
  1177   requires a some small amount of time. If processes work independently, then a
  1179   requires a small amount of time. If processes work independently,
  1178   low priority process can ``steal'' in this unguarded moment a lock for a
  1180   then a low priority process can ``steal'' in such an unguarded
  1179   resource that was supposed allow a high-priority process to run next. Thus
  1181   moment a lock for a resource that was supposed allow a high-priority
  1180   the problem of Priority Inversion is not really prevented. It seems 
  1182   process to run next. Thus the problem of Priority Inversion is not
  1181   difficult to design a PIP-algorithm with a meaningful correctness 
  1183   really prevented. It seems difficult to design a PIP-algorithm with
  1182   property on independent multi-processor systems.  We can imagine PIP 
  1184   a meaningful correctness property on a multi-processor systems where
  1183   to be of use in a situation where
  1185   processes work independently.  We can imagine PIP to be of use in
  1184   processes are not independent, but coordinated via a master
  1186   situations where processes are \emph{not} independent, but
  1185   process that distributes work over some slave processes. However a
  1187   coordinated via a master process that distributes work over some
  1186   formal investigation of this is beyond the scope of this paper.
  1188   slave processes. However, a formal investigation of this is beyond
  1187   We are not aware of any proofs in this area, not even informal ones.
  1189   the scope of this paper.  We are not aware of any proofs in this
  1188  
  1190   area, not even informal ones.
  1189   Our formalisation consists of 6894 of readable Isabelle/Isar code, with some
  1191 
  1190   apply-scripts interspersed. The formal model is 385 lines long; the 
  1192   The most closely related work to ours is the formal verification in
  1191   formal correctness proof 3777 lines. The properties relevant for an
  1193   PVS for Priority Ceiling done by Dutertre \cite{dutertre99b}. His formalisation
  1192   implementation are 1964 lines long; Auxlliary definitions and notions are 
  1194   consists of 407 lemmas and 2500 lines of ``specification'' (we do not
  1193   768 lines.
  1195   know whether this includes also code for proofs).  Our formalisation
  1194   
  1196   consists of around 210 lemmas and overall 6950 lines of readable Isabelle/Isar
  1195 
  1197   code with a few apply-scripts interspersed. The formal model of PIP
       
  1198   is 385 lines long; the formal correctness proof 3800 lines. Some auxiliary
       
  1199   definitions and proofs took 770 lines of code. The properties relevant
       
  1200   for an implementation took 2000 lines.  Our code can be downloaded from
       
  1201   ...
       
  1202 
       
  1203   \bibliographystyle{plain}
       
  1204   \bibliography{root}
  1196 *}
  1205 *}
  1197 
  1206 
  1198 section {* Key properties \label{extension} *}
  1207 section {* Key properties \label{extension} *}
  1199 
  1208 
  1200 (*<*)
  1209 (*<*)
  1309   then.
  1318   then.
  1310   *}
  1319   *}
  1311 
  1320 
  1312 (*<*)
  1321 (*<*)
  1313 end
  1322 end
  1314 (*>*)
  1323 
  1315 
       
  1316 
       
  1317 section {* Related works \label{related} *}
       
  1318 
       
  1319 text {*
       
  1320   \begin{enumerate}
       
  1321   \item {\em Integrating Priority Inheritance Algorithms in the Real-Time Specification for Java}
       
  1322     \cite{Wellings07} models and verifies the combination of Priority Inheritance (PI) and 
       
  1323     Priority Ceiling Emulation (PCE) protocols in the setting of Java virtual machine 
       
  1324     using extended Timed Automata(TA) formalism of the UPPAAL tool. Although a detailed 
       
  1325     formal model of combined PI and PCE is given, the number of properties is quite 
       
  1326     small and the focus is put on the harmonious working of PI and PCE. Most key features of PI 
       
  1327     (as well as PCE) are not shown. Because of the limitation of the model checking technique
       
  1328     used there, properties are shown only for a small number of scenarios. Therefore, 
       
  1329     the verification does not show the correctness of the formal model itself in a 
       
  1330     convincing way.  
       
  1331   \item {\em Formal Development of Solutions for Real-Time Operating Systems with TLA+/TLC}
       
  1332     \cite{Faria08}. A formal model of PI is given in TLA+. Only 3 properties are shown 
       
  1333     for PI using model checking. The limitation of model checking is intrinsic to the work.
       
  1334   \item {\em Synchronous modeling and validation of priority inheritance schedulers}
       
  1335     \cite{Jahier09}. Gives a formal model
       
  1336     of PI and PCE in AADL (Architecture Analysis \& Design Language) and checked 
       
  1337     several properties using model checking. The number of properties shown there is 
       
  1338     less than here and the scale is also limited by the model checking technique. 
       
  1339   \item {\em The Priority Ceiling Protocol: Formalization and Analysis Using PVS}
       
  1340     \cite{dutertre99b}. Formalized another protocol for Priority Inversion in the 
       
  1341     interactive theorem proving system PVS.
       
  1342 \end{enumerate}
       
  1343 
       
  1344 
       
  1345   There are several works on inversion avoidance:
       
  1346   \begin{enumerate}
       
  1347   \item {\em Solving the group priority inversion problem in a timed asynchronous system}
       
  1348     \cite{Wang:2002:SGP}. The notion of Group Priority Inversion is introduced. The main 
       
  1349     strategy is still inversion avoidance. The method is by reordering requests 
       
  1350     in the setting of Client-Server.
       
  1351   \item {\em A Formalization of Priority Inversion} \cite{journals/rts/BabaogluMS93}. 
       
  1352     Formalized the notion of Priority 
       
  1353     Inversion and proposes methods to avoid it. 
       
  1354   \end{enumerate}
       
  1355 
       
  1356   {\em Examples of inaccurate specification of the protocol ???}.
       
  1357 
       
  1358 *}
       
  1359 
       
  1360 
       
  1361 (*<*)
       
  1362 end
  1324 end
  1363 (*>*)
  1325 (*>*)