anchor.diff:                  | _ ->
                       ()
   
  +        
           member x.Run (v : 'i) =
               lock x (fun () ->        
                   handler.run v
               )
   
           member x.Disassemble() =
  -            let code = List()
  -            let mutable current = prolog
  -            while current <> epilog do
  -                if current <> prolog then
  -                    match current.Storage with
  -                        | None -> code.Add [||]
  -                        | Some s -> code.Add(handler.disassemble s |> List.toArray)
  -
  -                match current.Storage, current.Next.Storage with
  -                    | Some l, Some r -> 
  -                        if not (handler.isNext l r) then
  -                            failwith "bad pointers"
  -                    | _ -> ()
  -
  -                current <- current.Next
  -            code.ToArray()
  +            lock x (fun () ->        
  +                let code = List()
  +                let mutable current = prolog
  +                while current <> epilog do
  +                    if current <> prolog then
  +                        match current.Storage with
  +                            | None -> code.Add [||]
  +                            | Some s -> code.Add(handler.disassemble s |> List.toArray)
  +
  +                    match current.Storage, current.Next.Storage with
  +                        | Some l, Some r -> 
  +                            if not (handler.isNext l r) then
  +                                failwith "bad pointers"
  +                        | _ -> ()
  +
  +                    current <- current.Next
  +                code.ToArray()
  +            )
   
           member x.Update caller = 
  +            // update basically runs in 4 stages:
  +            //  1) process input deltas adding/removing fragments
  +            //  2) create code for fragments which need to be recompiled.
  +            //     recompile can be triggered either because they're new or their 
  +            //     predecessor changed and compileDelta depends on the it.
  +            //  3) write the code for all changed fragments to their underlying 
  +            //     (possibly native) representation. This is obviously needed for new
  +            //     fragments but also for the ones where some inner-instruction changed.
  +            //  4) link fragments appropriately where needed. Fragments must obviously be
  +            //     linked whenever Next changes but also when WriteContent() returns true
  +            //     (which is the case when the underlying representation has been moved)
  +            // known issues:
  +            //   - whenver an instruction changes the entire fragment is re-assembled and written
  +            //     as a whole. The write itself may not be too bad but the assemble-step 
  +            //     (at least in the native implementation) might be expensive
  +            //   - core-implementations (like CodeFragment) provide Append/Update/Clear function which
  +            //     are no longer optimal for this new implementation. 
  +            //     a possibly better API would be (where bool indicates if the fragment was moved)
  +            //       Write : list<list<Instruction>> -> bool * list<Handle>
  +            //       Update : Handle -> list<Instruction> -> bool
               x.EvaluateIfNeeded caller AdaptiveProgramStatistics.Zero (fun v ->
                   Interlocked.Increment(version) |> ignore
   
  +                // start by getting the deltas from our input-set
                   let deltas = reader.GetDelta x
   
  +                // get all fragments whose inner code-representation changed. 
                   let dirtySet = 
                       lock dirtyLock (fun () ->
                           let set = dirtySet
  
positive.code:     inherit IAdaptiveObject
      inherit IDisposable
      
      abstract member Update : IAdaptiveObject -> AdaptiveProgramStatistics
      abstract member Run : 'i -> unit
      
      abstract member Disassemble : unit -> obj
  
      abstract member AutoDefragmentation : bool with get, set
      abstract member StartDefragmentation : unit -> Task<TimeSpan>
  
      abstract member NativeCallCount : int
      abstract member FragmentCount : int
      abstract member ProgramSizeInBytes : int64
      abstract member TotalJumpDistanceInBytes : int64
  
  [<AllowNullLiteral>]
  
negative.code:                         set
                      )
  
                  // TODO: move to class-fields
                  let deadSet = HashSet()
                  let recompileSet = HashSet()
                  let relinkSet = HashSet()
  