Journal/Paper.thy
changeset 208 a5afc26b1d62
parent 207 d62b19b641c5
equal deleted inserted replaced
207:d62b19b641c5 208:a5afc26b1d62
   249   in PINTOS.  This fact, however, is important for an efficient
   249   in PINTOS.  This fact, however, is important for an efficient
   250   implementation of PIP, because we can give the lock to the thread
   250   implementation of PIP, because we can give the lock to the thread
   251   with the highest priority so that it terminates more quickly.  We
   251   with the highest priority so that it terminates more quickly.  We
   252   are also able to generalise the scheduler of Sha et
   252   are also able to generalise the scheduler of Sha et
   253   al.~\cite{Sha90} to the practically relevant case where critical
   253   al.~\cite{Sha90} to the practically relevant case where critical
   254   sections can overlap; see Figure~\ref{overlap} \emph{a)} below for
   254   sections can overlap; see Fig.~\ref{overlap} \emph{a)} for
   255   an example of this restriction. In the existing literature there is
   255   an example of this restriction. In the existing literature there is
   256   no proof and also no method for proving which covers this generalised
   256   no proof and also no proof method that covers this generalised
   257   case.
   257   case.
   258 
   258 
   259   \begin{figure}
   259   \begin{figure}
   260   \begin{center}
   260   \begin{center}
   261   \begin{tikzpicture}[scale=1]
   261   \begin{tikzpicture}[scale=1]
   425   @{thm actions_of_def[where ?s="s" and ?ths="ths", THEN eq_reflection]}.
   425   @{thm actions_of_def[where ?s="s" and ?ths="ths", THEN eq_reflection]}.
   426   \end{isabelle}
   426   \end{isabelle}
   427 
   427 
   428   \noindent
   428   \noindent
   429   where we use Isabelle's notation for list-comprehensions. This
   429   where we use Isabelle's notation for list-comprehensions. This
   430   notation is very similar to notation used in Haskell for list-comprehensions.  
   430   notation is very similar to the notation used in Haskell for list-comprehensions.  
   431   A \emph{precedence} of a thread @{text th} in a
   431   A \emph{precedence} of a thread @{text th} in a
   432   state @{text s} is the pair of natural numbers defined as
   432   state @{text s} is the pair of natural numbers defined as
   433   
   433   
   434   \begin{isabelle}\ \ \ \ \ %%%
   434   \begin{isabelle}\ \ \ \ \ %%%
   435   @{thm preced_def}
   435   @{thm preced_def}
   560   \caption{An instance of a Resource Allocation Graph (RAG).\label{RAGgraph}}
   560   \caption{An instance of a Resource Allocation Graph (RAG).\label{RAGgraph}}
   561   \end{figure}
   561   \end{figure}
   562 
   562 
   563   \noindent
   563   \noindent
   564   If there is no cycle, then every @{text RAG} can be pictured as a forest of trees, as
   564   If there is no cycle, then every @{text RAG} can be pictured as a forest of trees, as
   565   for example in Figure~\ref{RAGgraph}.
   565   for example in Fig.~\ref{RAGgraph}.
   566 
   566 
   567   Because of the @{text RAG}s, we will need to formalise some results
   567   Because of the @{text RAG}s, we will need to formalise some results
   568   about graphs.
   568   about graphs.
   569   It
   569   It
   570   seems for our purposes the most convenient representation of
   570   seems for our purposes the most convenient representation of
   607   @{thm ancestors_def[where ?r="rel" and ?x="node", THEN eq_reflection]}\\
   607   @{thm ancestors_def[where ?r="rel" and ?x="node", THEN eq_reflection]}\\
   608   \end{tabular}\\
   608   \end{tabular}\\
   609   \mbox{}\hfill\numbered{children}
   609   \mbox{}\hfill\numbered{children}
   610   \end{isabelle}
   610   \end{isabelle}
   611   
   611   
   612   \noindent Note that forests can have trees with infinte depth and
   612   \noindent Note that forests can have trees with infinite depth and
   613   containing nodes with infinitely many children.  A \emph{finite
   613   containing nodes with infinitely many children.  A \emph{finite
   614   forest} is a forest whose underlying relation is
   614   forest} is a forest whose underlying relation is
   615   well-founded\footnote{For \emph{well-founded} we use the quite natural
   615   well-founded\footnote{For \emph{well-founded} we use the quite natural
   616   definition from Isabelle/HOL.}
   616   definition from Isabelle/HOL.}
   617   and every node has finitely many children (is only finitely
   617   and every node has finitely many children (is only finitely
   650   \end{isabelle}
   650   \end{isabelle}
   651 
   651 
   652   \noindent This definition is the relation that one thread is waiting for
   652   \noindent This definition is the relation that one thread is waiting for
   653   another to release a resource, but the corresponding 
   653   another to release a resource, but the corresponding 
   654   resource is ``hidden''. 
   654   resource is ``hidden''. 
   655   In Figure~\ref{RAGgraph} this means the @{text TDG} connects 
   655   In Fig.~\ref{RAGgraph} this means the @{text TDG} connects 
   656   @{text "th\<^sub>1"} and @{text "th\<^sub>2"} to @{text "th\<^sub>0"}, which both wait for
   656   @{text "th\<^sub>1"} and @{text "th\<^sub>2"} to @{text "th\<^sub>0"}, which both wait for
   657   resource @{text "cs\<^sub>1"} to be released; and @{text "th\<^sub>3"} to @{text "th\<^sub>2"}, which
   657   resource @{text "cs\<^sub>1"} to be released; and @{text "th\<^sub>3"} to @{text "th\<^sub>2"}, which
   658   cannot make any progress unless @{text "th\<^sub>2"} makes progress. 
   658   cannot make any progress unless @{text "th\<^sub>2"} makes progress. 
   659   Similarly for the other threads.
   659   Similarly for the other threads.
   660   If
   660   If
   710 
   710 
   711   In the initial state, the scheduler starts with all resources unlocked (the corresponding 
   711   In the initial state, the scheduler starts with all resources unlocked (the corresponding 
   712   function is defined in \eqref{allunlocked}) and the
   712   function is defined in \eqref{allunlocked}) and the
   713   current precedence of every thread is initialised with @{term "Prc 0 0"}; that means 
   713   current precedence of every thread is initialised with @{term "Prc 0 0"}; that means 
   714   \mbox{@{abbrev initial_cprec}}. Therefore
   714   \mbox{@{abbrev initial_cprec}}. Therefore
   715   we have for the initial shedule state
   715   we have for the initial schedule state
   716 
   716 
   717   \begin{isabelle}\ \ \ \ \ %%%
   717   \begin{isabelle}\ \ \ \ \ %%%
   718   \begin{tabular}{@ {}l}
   718   \begin{tabular}{@ {}l}
   719   @{thm (lhs) schs.simps(1)} @{text "\<equiv>"}\\ 
   719   @{thm (lhs) schs.simps(1)} @{text "\<equiv>"}\\ 
   720   \hspace{5mm}@{term "(|wq_fun = all_unlocked, cprec_fun = (\<lambda>_::thread. Prc 0 0)|)"}
   720   \hspace{5mm}@{term "(|wq_fun = all_unlocked, cprec_fun = (\<lambda>_::thread. Prc 0 0)|)"}
  1242   %%%}
  1242   %%%}
  1243 
  1243 
  1244 %  \endnote{{\bf OUTLINE}
  1244 %  \endnote{{\bf OUTLINE}
  1245 
  1245 
  1246 %  Since @{term "th"} is the most urgent thread, if it is somehow
  1246 %  Since @{term "th"} is the most urgent thread, if it is somehow
  1247 %  blocked, people want to know why and wether this blocking is
  1247 %  blocked, people want to know why and whether this blocking is
  1248 %  reasonable.
  1248 %  reasonable.
  1249 
  1249 
  1250 %  @{thm [source] th_blockedE} @{thm th_blockedE}
  1250 %  @{thm [source] th_blockedE} @{thm th_blockedE}
  1251 
  1251 
  1252 %  if @{term "th"} is blocked, then there is a path leading from 
  1252 %  if @{term "th"} is blocked, then there is a path leading from 
  1260 
  1260 
  1261 %  THEN
  1261 %  THEN
  1262 
  1262 
  1263 %  @{thm [source] vat_t.th_chain_to_ready} @{thm vat_t.th_chain_to_ready}
  1263 %  @{thm [source] vat_t.th_chain_to_ready} @{thm vat_t.th_chain_to_ready}
  1264 
  1264 
  1265 %  It is basic propery with non-trival proof. 
  1265 %  It is basic property with non-trivial proof. 
  1266 
  1266 
  1267 %  THEN
  1267 %  THEN
  1268 
  1268 
  1269 %  @{thm [source] max_preced} @{thm max_preced}
  1269 %  @{thm [source] max_preced} @{thm max_preced}
  1270 
  1270 
  1340 %  to @{term "preced th (t @ s)"}.
  1340 %  to @{term "preced th (t @ s)"}.
  1341 
  1341 
  1342   %Let me distinguish between cp (current precedence) and assigned precedence (the precedence the
  1342   %Let me distinguish between cp (current precedence) and assigned precedence (the precedence the
  1343   %thread ``normally'' has).
  1343   %thread ``normally'' has).
  1344   %So we want to show what the cp of th' is in state t @ s.
  1344   %So we want to show what the cp of th' is in state t @ s.
  1345   %We look at all the assingned precedences in the subgraph starting from th'
  1345   %We look at all the assigned precedences in the subgraph starting from th'
  1346   %We are looking for the maximum of these assigned precedences.
  1346   %We are looking for the maximum of these assigned precedences.
  1347   %This subgraph must contain the thread th, which actually has the highest precednence
  1347   %This subgraph must contain the thread th, which actually has the highest precedence
  1348   %so cp of th' in t @ s has this (assigned) precedence of th
  1348   %so cp of th' in t @ s has this (assigned) precedence of th
  1349   %We know that cp (t @ s) th' 
  1349   %We know that cp (t @ s) th' 
  1350   %is the Maximum of the threads in the subgraph starting from th'
  1350   %is the Maximum of the threads in the subgraph starting from th'
  1351   %this happens to be the precedence of th
  1351   %this happens to be the precedence of th
  1352   %th has the highest precedence of all threads
  1352   %th has the highest precedence of all threads
  1431 %  we have @{term "cp (s' @ s) th' < prec th (s' @ s)"}.
  1431 %  we have @{term "cp (s' @ s) th' < prec th (s' @ s)"}.
  1432 %  Since @{text "prec th (s' @ s)"} is already the highest 
  1432 %  Since @{text "prec th (s' @ s)"} is already the highest 
  1433 %  @{term "cp (s' @ s) th"} can not be higher than this and can not be lower either (by 
  1433 %  @{term "cp (s' @ s) th"} can not be higher than this and can not be lower either (by 
  1434 %  definition of @{term "cp"}). Consequently, we have @{term "prec th (s' @ s) = cp (s' @ s) th"}.
  1434 %  definition of @{term "cp"}). Consequently, we have @{term "prec th (s' @ s) = cp (s' @ s) th"}.
  1435 %  Finally we have @{term "cp (s' @ s) th' < cp (s' @ s) th"}.
  1435 %  Finally we have @{term "cp (s' @ s) th' < cp (s' @ s) th"}.
  1436 %  By defintion of @{text "running"}, @{text "th'"} can not be running in state
  1436 %  By definition of @{text "running"}, @{text "th'"} can not be running in state
  1437 %  @{text "s' @ s"}, as we had to show.\qed
  1437 %  @{text "s' @ s"}, as we had to show.\qed
  1438 %  \end{proof}
  1438 %  \end{proof}
  1439 
  1439 
  1440 %  \noindent
  1440 %  \noindent
  1441 %  Since @{text "th'"} is not able to run in state @{text "s' @ s"}, it is not able to 
  1441 %  Since @{text "th'"} is not able to run in state @{text "s' @ s"}, it is not able to 
  1509   %  thread does not hold any critical resource, therefore no thread can depend on it
  1509   %  thread does not hold any critical resource, therefore no thread can depend on it
  1510   %  (@{text "count_eq_dependants"}):
  1510   %  (@{text "count_eq_dependants"}):
  1511   %  @  {thm [display] count_eq_dependants}
  1511   %  @  {thm [display] count_eq_dependants}
  1512   %\end{enumerate}
  1512   %\end{enumerate}
  1513 
  1513 
  1514   %The reason that only threads which already held some resoures
  1514   %The reason that only threads which already held some resources
  1515   %can be running and block @{text "th"} is that if , otherwise, one thread 
  1515   %can be running and block @{text "th"} is that if , otherwise, one thread 
  1516   %does not hold any resource, it may never have its prioirty raised
  1516   %does not hold any resource, it may never have its priority raised
  1517   %and will not get a chance to run. This fact is supported by 
  1517   %and will not get a chance to run. This fact is supported by 
  1518   %lemma @{text "moment_blocked"}:
  1518   %lemma @{text "moment_blocked"}:
  1519   %@   {thm [display] moment_blocked}
  1519   %@   {thm [display] moment_blocked}
  1520   %When instantiating  @{text "i"} to @{text "0"}, the lemma means threads which did not hold any
  1520   %When instantiating  @{text "i"} to @{text "0"}, the lemma means threads which did not hold any
  1521   %resource in state @{text "s"} will not have a change to run latter. Rephrased, it means 
  1521   %resource in state @{text "s"} will not have a change to run latter. Rephrased, it means 
  1577   %if every such thread can release all its resources in finite duration, then after finite
  1577   %if every such thread can release all its resources in finite duration, then after finite
  1578   %duration, none of them may block @{term "th"} anymore. So, no priority inversion may happen
  1578   %duration, none of them may block @{term "th"} anymore. So, no priority inversion may happen
  1579   %then.
  1579   %then.
  1580 
  1580 
  1581  % NOTE: about bounds in sha et al and ours: they prove a bound on the length of individual
  1581  % NOTE: about bounds in sha et al and ours: they prove a bound on the length of individual
  1582  % blocages. We prove a bound for the overall-blockage.
  1582  % blockages. We prove a bound for the overall-blockage.
  1583 
  1583 
  1584  % There are low priority threads, 
  1584  % There are low priority threads, 
  1585  % which do not hold any resources, 
  1585  % which do not hold any resources, 
  1586  % such thread will not block th. 
  1586  % such thread will not block th. 
  1587  % Their Theorem 3 does not exclude such threads.
  1587  % Their Theorem 3 does not exclude such threads.
  1588 
  1588 
  1589  % There are resources, which are not held by any low prioirty threads,
  1589  % There are resources, which are not held by any low priority threads,
  1590  % such resources can not cause blockage of th neither. And similiary, 
  1590  % such resources can not cause blockage of th neither. And similiary, 
  1591  % theorem 6 does not exlude them.
  1591  % theorem 6 does not exclude them.
  1592 
  1592 
  1593  % Our one bound excudle them by using a different formaulation. "
  1593  % Our one bound exclude them by using a different formulation. "
  1594 
  1594 
  1595   *}
  1595   *}
  1596 (*<*)
  1596 (*<*)
  1597 end
  1597 end
  1598 (*>*)
  1598 (*>*)
  1682   \begin{isabelle}\ \ \ \ \ %%%
  1682   \begin{isabelle}\ \ \ \ \ %%%
  1683   @{thm blockers_def[THEN eq_reflection]}
  1683   @{thm blockers_def[THEN eq_reflection]}
  1684   \end{isabelle}
  1684   \end{isabelle}
  1685 
  1685 
  1686   \noindent This set contains all threads that are not detached in
  1686   \noindent This set contains all threads that are not detached in
  1687   state @{text s}. According to our definiton of @{text "detached"},
  1687   state @{text s}. According to our definition of @{text "detached"},
  1688   this means a thread in @{text "blockers"} either holds or waits for
  1688   this means a thread in @{text "blockers"} either holds or waits for
  1689   some resource in state @{text s} . Our Thm.~1 implies that only 
  1689   some resource in state @{text s} . Our Thm.~1 implies that only 
  1690   these threads can all potentially block @{text th} after state
  1690   these threads can all potentially block @{text th} after state
  1691   @{text s}. We need to make the following assumption about the
  1691   @{text s}. We need to make the following assumption about the
  1692   threads in the @{text "blockers"}-set:
  1692   threads in the @{text "blockers"}-set:
  1835   \end{proof}
  1835   \end{proof}
  1836 
  1836 
  1837   \noindent This theorem is the main conclusion we obtain for the
  1837   \noindent This theorem is the main conclusion we obtain for the
  1838   Priority Inheritance Protocol. It is based on the fact that the set of
  1838   Priority Inheritance Protocol. It is based on the fact that the set of
  1839   @{text blockers} is fixed at state @{text s} when @{text th} becomes
  1839   @{text blockers} is fixed at state @{text s} when @{text th} becomes
  1840   the thread with highest priority. Then no additional blocker of
  1840   the thread with the highest priority. Then no additional blocker of
  1841   @{text th} can appear after the state @{text s}. And in this way we
  1841   @{text th} can appear after the state @{text s}. And in this way we
  1842   can bound the number of states where the thread @{text th} with the
  1842   can bound the number of states where the thread @{text th} with the
  1843   highest priority is prevented from running.
  1843   highest priority is prevented from running.
  1844   Our bound does not depend on the restriction of well-nested critical 
  1844   Our bound does not depend on the restriction of well-nested critical 
  1845   sections in the Priority Inheritance Protocol as imposed by Sha et al.  
  1845   sections in the Priority Inheritance Protocol as imposed by Sha et al.  
  1873   \noindent
  1873   \noindent
  1874   That means the current precedence of a thread @{text th} can be
  1874   That means the current precedence of a thread @{text th} can be
  1875   computed by considering the static precedence of @{text th}
  1875   computed by considering the static precedence of @{text th}
  1876   and 
  1876   and 
  1877   the current precedences of the children of @{text th}. Their 
  1877   the current precedences of the children of @{text th}. Their 
  1878   @{text "cprec"}s, in general, need to be computed by recursively decending into 
  1878   @{text "cprec"}s, in general, need to be computed by recursively descending into 
  1879   deeper ``levels'' of the @{text TDG}. 
  1879   deeper ``levels'' of the @{text TDG}. 
  1880   However, the current precedence of a thread @{text th}, say, 
  1880   However, the current precedence of a thread @{text th}, say, 
  1881   only needs to be recomputed when @{text "(i)"} its static
  1881   only needs to be recomputed when @{text "(i)"} its static
  1882   precedence is re-set or when @{text "(ii)"} one of
  1882   precedence is re-set or when @{text "(ii)"} one of
  1883   its children changes its current precedence or when @{text "(iii)"} the children set changes
  1883   its children changes its current precedence or when @{text "(iii)"} the children set changes
  1897   in response to each kind of events.\smallskip
  1897   in response to each kind of events.\smallskip
  1898 *}
  1898 *}
  1899 
  1899 
  1900 text {*
  1900 text {*
  1901   \noindent
  1901   \noindent
  1902   \colorbox{mygrey}{@{term "Create th prio"}:} We assume that the current state @{text s} and 
  1902   \colorbox{mygrey}{@{term "Create th prio"}:} \\ We assume that the current state @{text s} and 
  1903   the next state @{term "e#s"}, whereby \mbox{@{term "e \<equiv> Create th prio"}}, are both valid (meaning the event
  1903   the next state @{term "e#s"}, whereby \mbox{@{term "e \<equiv> Create th prio"}}, are both valid (meaning the event
  1904   @{text "Create"} is allowed to occur in @{text s}). In this situation we can show that
  1904   @{text "Create"} is allowed to occur in @{text s}). In this situation we can show that
  1905 
  1905 
  1906   \begin{isabelle}\ \ \ \ \ %%%
  1906   \begin{isabelle}\ \ \ \ \ %%%
  1907   \begin{tabular}{@ {}l}
  1907   \begin{tabular}{@ {}l}
  1918   \smallskip
  1918   \smallskip
  1919   *}
  1919   *}
  1920 
  1920 
  1921 text {*
  1921 text {*
  1922   \noindent
  1922   \noindent
  1923   \colorbox{mygrey}{@{term "Exit th"}:} We again assume that the current state @{text s} and 
  1923   \colorbox{mygrey}{@{term "Exit th"}:}\\ We again assume that the current state @{text s} and 
  1924   the next state @{term "e#s"}, whereby this time  @{term "e \<equiv> Exit th"}, are both valid. We can show that
  1924   the next state @{term "e#s"}, whereby this time  @{term "e \<equiv> Exit th"}, are both valid. We can show that
  1925 
  1925 
  1926   \begin{isabelle}\ \ \ \ \ %%%
  1926   \begin{isabelle}\ \ \ \ \ %%%
  1927   \begin{tabular}{@ {}l}
  1927   \begin{tabular}{@ {}l}
  1928   @{thm (concl) valid_trace_exit.RAG_es}, and\\
  1928   @{thm (concl) valid_trace_exit.RAG_es}, and\\
  1938   \smallskip
  1938   \smallskip
  1939 *}
  1939 *}
  1940 
  1940 
  1941 text {*
  1941 text {*
  1942   \noindent
  1942   \noindent
  1943   \colorbox{mygrey}{@{term "Set th prio"}:} We assume that @{text s} and 
  1943   \colorbox{mygrey}{@{term "Set th prio"}:}\\ We assume that @{text s} and 
  1944   @{term "e#s"} with @{term "e \<equiv> Set th prio"} are both valid. We can show that
  1944   @{term "e#s"} with @{term "e \<equiv> Set th prio"} are both valid. We can show that
  1945 
  1945 
  1946   \begin{isabelle}\ \ \ \ \ %%%
  1946   \begin{isabelle}\ \ \ \ \ %%%
  1947   \begin{tabular}{@ {}l}
  1947   \begin{tabular}{@ {}l}
  1948   @{thm (concl) valid_trace_set.RAG_es}, and\\
  1948   @{thm (concl) valid_trace_set.RAG_es}, and\\
  1987   \smallskip
  1987   \smallskip
  1988   *}
  1988   *}
  1989 
  1989 
  1990 text {*
  1990 text {*
  1991   \noindent
  1991   \noindent
  1992   \colorbox{mygrey}{@{term "V th cs"}:} We assume that @{text s} and 
  1992   \colorbox{mygrey}{@{term "V th cs"}:}\\ We assume that @{text s} and 
  1993   @{term "e#s"} with @{text e} being @{term "V th cs"} are both valid. 
  1993   @{term "e#s"} with @{text e} being @{term "V th cs"} are both valid. 
  1994   We have to consider two
  1994   We have to consider two
  1995   subcases: one where there is a thread to ``take over'' the released
  1995   subcases: one where there is a thread to ``take over'' the released
  1996   resource @{text cs}, and one where there is not. Let us consider them
  1996   resource @{text cs}, and one where there is not. Let us consider them
  1997   in turn. Suppose in state @{text s}, the thread @{text th'} takes over
  1997   in turn. Suppose in state @{text s}, the thread @{text th'} takes over
  2055   \end{isabelle}
  2055   \end{isabelle}
  2056   *}
  2056   *}
  2057 
  2057 
  2058 text {*
  2058 text {*
  2059   \noindent
  2059   \noindent
  2060   \colorbox{mygrey}{@{term "P th cs"}:} We assume that @{text s} and 
  2060   \colorbox{mygrey}{@{term "P th cs"}:}\\ We assume that @{text s} and 
  2061   @{term "e#s"} with @{term "e \<equiv> P th cs"} are both valid. 
  2061   @{term "e#s"} with @{term "e \<equiv> P th cs"} are both valid. 
  2062   We again have to analyse two subcases, namely
  2062   We again have to analyse two subcases, namely
  2063   the one where @{text cs} is not locked, and one where it is. We 
  2063   the one where @{text cs} is not locked, and one where it is. We 
  2064   treat the former case
  2064   treat the former case
  2065   first by showing that
  2065   first by showing that
  2073 
  2073 
  2074   \noindent This means we need to add a holding edge to the @{text
  2074   \noindent This means we need to add a holding edge to the @{text
  2075   RAG}. However, note that while the @{text RAG} changes the corresponding
  2075   RAG}. However, note that while the @{text RAG} changes the corresponding
  2076   @{text TDG} does not change. Together with the fact that the
  2076   @{text TDG} does not change. Together with the fact that the
  2077   precedences of all threads are unchanged, no @{text cprec} value is
  2077   precedences of all threads are unchanged, no @{text cprec} value is
  2078   changed. Therefore, no recalucation of the @{text cprec} value 
  2078   changed. Therefore, no recalculation of the @{text cprec} value 
  2079   of any thread @{text "th''"} is needed.
  2079   of any thread @{text "th''"} is needed.
  2080 
  2080 
  2081 *} 
  2081 *} 
  2082 
  2082 
  2083 text {*
  2083 text {*
  2098   @{text th} we need
  2098   @{text th} we need
  2099   to follow the edges in the @{text TDG} and recompute the @{term
  2099   to follow the edges in the @{text TDG} and recompute the @{term
  2100   "cprecs"}. Whereas in all other event we might have to make
  2100   "cprecs"}. Whereas in all other event we might have to make
  2101   modifications to the @{text "RAG"}, no recalculation of @{text
  2101   modifications to the @{text "RAG"}, no recalculation of @{text
  2102   cprec} depends on the @{text RAG}. This is the only case where
  2102   cprec} depends on the @{text RAG}. This is the only case where
  2103   the recalulation needs to take the connections in the @{text RAG} into
  2103   the recalculation needs to take the connections in the @{text RAG} into
  2104   account.
  2104   account.
  2105   To do this we can start from @{term "th"} and follow the
  2105   To do this we can start from @{term "th"} and follow the
  2106   @{term "children"}-edges to recompute the @{term "cp"} of every
  2106   @{term "children"}-edges to recompute the @{term "cp"} of every
  2107   thread encountered on the way using Lemma~\ref{childrenlem}. 
  2107   thread encountered on the way using Lemma~\ref{childrenlem}. 
  2108   This means the recomputation can be done locally (level-by-level)
  2108   This means the recomputation can be done locally (level-by-level)
  2174   in a queue. Both functions take an extra argument that specifies the
  2174   in a queue. Both functions take an extra argument that specifies the
  2175   comparison function used for organising the priority queue.
  2175   comparison function used for organising the priority queue.
  2176   
  2176   
  2177   Apart from having to implement relatively complex data\-structures in C
  2177   Apart from having to implement relatively complex data\-structures in C
  2178   using pointers, our experience with the implementation has been very positive: our specification 
  2178   using pointers, our experience with the implementation has been very positive: our specification 
  2179   and formalisation of PIP translates smoothly to an efficent implementation in PINTOS. 
  2179   and formalisation of PIP translates smoothly to an efficient implementation in PINTOS. 
  2180   Let us illustrate this with the C-code for the function @{ML_text "lock_acquire"}, 
  2180   Let us illustrate this with the C-code for the function @{ML_text "lock_acquire"}, 
  2181   shown in Figure~\ref{code}.  This function implements the operation of requesting and, if free, 
  2181   shown in Figure~\ref{code}.  This function implements the operation of requesting and, if free, 
  2182   locking of a resource by the current running thread. The convention in the PINTOS
  2182   locking of a resource by the current running thread. The convention in the PINTOS
  2183   code is to use the terminology \emph{locks} rather than resources. 
  2183   code is to use the terminology \emph{locks} rather than resources. 
  2184   A lock is represented as a pointer to the structure {\tt lock} (Line 1). 
  2184   A lock is represented as a pointer to the structure {\tt lock} (Line 1). 
  2275   the lock (Line 28), and finally update the queue of locks the current 
  2275   the lock (Line 28), and finally update the queue of locks the current 
  2276   thread already possesses (Line 29).
  2276   thread already possesses (Line 29).
  2277   The very last step is to enable interrupts again thus leaving the protected section.
  2277   The very last step is to enable interrupts again thus leaving the protected section.
  2278   
  2278   
  2279 
  2279 
  2280   Similar operations need to be implementated for the @{ML_text lock_release} function, which
  2280   Similar operations need to be implemented for the @{ML_text lock_release} function, which
  2281   we however do not show. The reader should note though that we did \emph{not} verify our C-code. 
  2281   we however do not show. The reader should note though that we did \emph{not} verify our C-code. 
  2282   This is in contrast, for example, to the work on seL4, which actually verified in Isabelle/HOL
  2282   This is in contrast, for example, to the work on seL4, which actually verified in Isabelle/HOL
  2283   that their C-code satisfies its specification, though this specification does not contain 
  2283   that their C-code satisfies its specification, though this specification does not contain 
  2284   anything about PIP \cite{sel4}.
  2284   anything about PIP \cite{sel4}.
  2285   Our verification of PIP however provided us with (formally proven) insights on how to design 
  2285   Our verification of PIP however provided us with (formally proven) insights on how to design 
  2314   explain how to use various implementations of PIP and abstractly
  2314   explain how to use various implementations of PIP and abstractly
  2315   discuss their properties, but surprisingly lack most details important for a
  2315   discuss their properties, but surprisingly lack most details important for a
  2316   programmer who wants to implement PIP (similarly Sha et al.~\cite{Sha90}).  
  2316   programmer who wants to implement PIP (similarly Sha et al.~\cite{Sha90}).  
  2317   That this is an issue in practice is illustrated by the
  2317   That this is an issue in practice is illustrated by the
  2318   email from Baker we cited in the Introduction. We achieved also this
  2318   email from Baker we cited in the Introduction. We achieved also this
  2319   goal: The formalisation allowed us to efficently implement our version
  2319   goal: The formalisation allowed us to efficiently implement our version
  2320   of PIP on top of PINTOS, a simple instructional operating system for the x86 
  2320   of PIP on top of PINTOS, a simple instructional operating system for the x86 
  2321   architecture implemented by Pfaff \cite{PINTOS}. It also gives the first author enough data to enable
  2321   architecture implemented by Pfaff \cite{PINTOS}. It also gives the first author enough data to enable
  2322   his undergraduate students to implement PIP (as part of their OS course).
  2322   his undergraduate students to implement PIP (as part of their OS course).
  2323   A byproduct of our formalisation effort is that nearly all
  2323   A byproduct of our formalisation effort is that nearly all
  2324   design choices for the implementation of PIP scheduler are backed up with a proved
  2324   design choices for the implementation of PIP scheduler are backed up with a proved