src/Pure/System/session.scala
changeset 54521 744ea0025e11
parent 54519 5fed81762406
child 54559 39d91cac6e91
equal deleted inserted replaced
54520:cee77d2e9582 54521:744ea0025e11
    23 
    23 
    24   //{{{
    24   //{{{
    25   case class Statistics(props: Properties.T)
    25   case class Statistics(props: Properties.T)
    26   case class Global_Options(options: Options)
    26   case class Global_Options(options: Options)
    27   case object Caret_Focus
    27   case object Caret_Focus
    28   case class Raw_Edits(edits: List[Document.Edit_Text])
    28   case class Raw_Edits(doc_blobs: Document.Blobs, edits: List[Document.Edit_Text])
    29   case class Dialog_Result(id: Document_ID.Generic, serial: Long, result: String)
    29   case class Dialog_Result(id: Document_ID.Generic, serial: Long, result: String)
    30   case class Commands_Changed(
    30   case class Commands_Changed(
    31     assignment: Boolean, nodes: Set[Document.Node.Name], commands: Set[Command])
    31     assignment: Boolean, nodes: Set[Document.Node.Name], commands: Set[Command])
    32 
    32 
    33   sealed abstract class Phase
    33   sealed abstract class Phase
   165   /** pipelined change parsing **/
   165   /** pipelined change parsing **/
   166 
   166 
   167   //{{{
   167   //{{{
   168   private case class Text_Edits(
   168   private case class Text_Edits(
   169     previous: Future[Document.Version],
   169     previous: Future[Document.Version],
       
   170     doc_blobs: Document.Blobs,
   170     text_edits: List[Document.Edit_Text],
   171     text_edits: List[Document.Edit_Text],
   171     version_result: Promise[Document.Version])
   172     version_result: Promise[Document.Version])
   172 
   173 
   173   private val (_, change_parser) = Simple_Thread.actor("change_parser", daemon = true)
   174   private val (_, change_parser) = Simple_Thread.actor("change_parser", daemon = true)
   174   {
   175   {
   175     var finished = false
   176     var finished = false
   176     while (!finished) {
   177     while (!finished) {
   177       receive {
   178       receive {
   178         case Stop => finished = true; reply(())
   179         case Stop => finished = true; reply(())
   179 
   180 
   180         case Text_Edits(previous, text_edits, version_result) =>
   181         case Text_Edits(previous, doc_blobs, text_edits, version_result) =>
   181           val prev = previous.get_finished
   182           val prev = previous.get_finished
   182           val (all_blobs, doc_edits, version) =
   183           val (doc_edits, version) =
   183             Timing.timeit("Thy_Load.text_edits", timing) {
   184             Timing.timeit("Thy_Load.text_edits", timing) {
   184               thy_load.text_edits(reparse_limit, prev, text_edits)
   185               thy_load.text_edits(reparse_limit, prev, doc_blobs, text_edits)
   185             }
   186             }
   186           version_result.fulfill(version)
   187           version_result.fulfill(version)
   187           sender ! Change(all_blobs, doc_edits, prev, version)
   188           sender ! Change(doc_blobs, doc_edits, prev, version)
   188 
   189 
   189         case bad => System.err.println("change_parser: ignoring bad message " + bad)
   190         case bad => System.err.println("change_parser: ignoring bad message " + bad)
   190       }
   191       }
   191     }
   192     }
   192   }
   193   }
   248   /* actor messages */
   249   /* actor messages */
   249 
   250 
   250   private case class Start(args: List[String])
   251   private case class Start(args: List[String])
   251   private case class Cancel_Exec(exec_id: Document_ID.Exec)
   252   private case class Cancel_Exec(exec_id: Document_ID.Exec)
   252   private case class Change(
   253   private case class Change(
   253     all_blobs: Map[Document.Node.Name, Bytes],
   254     doc_blobs: Document.Blobs,
   254     doc_edits: List[Document.Edit_Command],
   255     doc_edits: List[Document.Edit_Command],
   255     previous: Document.Version,
   256     previous: Document.Version,
   256     version: Document.Version)
   257     version: Document.Version)
   257   private case class Protocol_Command(name: String, args: List[String])
   258   private case class Protocol_Command(name: String, args: List[String])
   258   private case class Messages(msgs: List[Isabelle_Process.Message])
   259   private case class Messages(msgs: List[Isabelle_Process.Message])
   347     }
   348     }
   348 
   349 
   349 
   350 
   350     /* raw edits */
   351     /* raw edits */
   351 
   352 
   352     def handle_raw_edits(edits: List[Document.Edit_Text])
   353     def handle_raw_edits(doc_blobs: Document.Blobs, edits: List[Document.Edit_Text])
   353     //{{{
   354     //{{{
   354     {
   355     {
   355       prover.get.discontinue_execution()
   356       prover.get.discontinue_execution()
   356 
   357 
   357       val previous = global_state().history.tip.version
   358       val previous = global_state().history.tip.version
   358       val version = Future.promise[Document.Version]
   359       val version = Future.promise[Document.Version]
   359       val change = global_state >>> (_.continue_history(previous, edits, version))
   360       val change = global_state >>> (_.continue_history(previous, edits, version))
   360 
   361 
   361       raw_edits.event(Session.Raw_Edits(edits))
   362       raw_edits.event(Session.Raw_Edits(doc_blobs, edits))
   362       change_parser ! Text_Edits(previous, edits, version)
   363       change_parser ! Text_Edits(previous, doc_blobs, edits, version)
   363     }
   364     }
   364     //}}}
   365     //}}}
   365 
   366 
   366 
   367 
   367     /* resulting changes */
   368     /* resulting changes */
   377       {
   378       {
   378         for {
   379         for {
   379           digest <- command.blobs_digests
   380           digest <- command.blobs_digests
   380           if !global_state().defined_blob(digest)
   381           if !global_state().defined_blob(digest)
   381         } {
   382         } {
   382           change.all_blobs.collectFirst({ case (_, b) if b.sha1_digest == digest => b }) match {
   383           change.doc_blobs.collectFirst({ case (_, b) if b.sha1_digest == digest => b }) match {
   383             case Some(blob) =>
   384             case Some(blob) =>
   384               global_state >> (_.define_blob(digest))
   385               global_state >> (_.define_blob(digest))
   385               prover.get.define_blob(blob)
   386               prover.get.define_blob(blob)
   386             case None => System.err.println("Missing blob for SHA1 digest " + digest)
   387             case None => System.err.println("Missing blob for SHA1 digest " + digest)
   387           }
   388           }
   521           reply(())
   522           reply(())
   522 
   523 
   523         case Update_Options(options) if prover.isDefined =>
   524         case Update_Options(options) if prover.isDefined =>
   524           if (is_ready) {
   525           if (is_ready) {
   525             prover.get.options(options)
   526             prover.get.options(options)
   526             handle_raw_edits(Nil)
   527             handle_raw_edits(Map.empty, Nil)
   527           }
   528           }
   528           global_options.event(Session.Global_Options(options))
   529           global_options.event(Session.Global_Options(options))
   529           reply(())
   530           reply(())
   530 
   531 
   531         case Cancel_Exec(exec_id) if prover.isDefined =>
   532         case Cancel_Exec(exec_id) if prover.isDefined =>
   532           prover.get.cancel_exec(exec_id)
   533           prover.get.cancel_exec(exec_id)
   533 
   534 
   534         case Session.Raw_Edits(edits) if prover.isDefined =>
   535         case Session.Raw_Edits(doc_blobs, edits) if prover.isDefined =>
   535           handle_raw_edits(edits)
   536           handle_raw_edits(doc_blobs, edits)
   536           reply(())
   537           reply(())
   537 
   538 
   538         case Session.Dialog_Result(id, serial, result) if prover.isDefined =>
   539         case Session.Dialog_Result(id, serial, result) if prover.isDefined =>
   539           prover.get.dialog_result(serial, result)
   540           prover.get.dialog_result(serial, result)
   540           handle_output(new Isabelle_Process.Output(Protocol.Dialog_Result(id, serial, result)))
   541           handle_output(new Isabelle_Process.Output(Protocol.Dialog_Result(id, serial, result)))
   583   def protocol_command(name: String, args: String*)
   584   def protocol_command(name: String, args: String*)
   584   { session_actor ! Protocol_Command(name, args.toList) }
   585   { session_actor ! Protocol_Command(name, args.toList) }
   585 
   586 
   586   def cancel_exec(exec_id: Document_ID.Exec) { session_actor ! Cancel_Exec(exec_id) }
   587   def cancel_exec(exec_id: Document_ID.Exec) { session_actor ! Cancel_Exec(exec_id) }
   587 
   588 
   588   def update(edits: List[Document.Edit_Text])
   589   def update(doc_blobs: Document.Blobs, edits: List[Document.Edit_Text])
   589   { if (!edits.isEmpty) session_actor !? Session.Raw_Edits(edits) }
   590   { if (!edits.isEmpty) session_actor !? Session.Raw_Edits(doc_blobs, edits) }
   590 
   591 
   591   def update_options(options: Options)
   592   def update_options(options: Options)
   592   { session_actor !? Update_Options(options) }
   593   { session_actor !? Update_Options(options) }
   593 
   594 
   594   def dialog_result(id: Document_ID.Generic, serial: Long, result: String)
   595   def dialog_result(id: Document_ID.Generic, serial: Long, result: String)