anchor.diff:  
       % If the new node replaced a new, remove all timer and access time
       % information from the state
  -    {TmpNTimers, TmpNAccess} = case Deleted of
  +    TmpNTimers = case Replace of
           none ->
  -            {PrevNTimers, PrevNAccess};
  -        {DID, DIP, DPort} ->
  -            {cancel_node_timer(DID, DIP, DPort, PrevNTimers),
  -             clear_node_access(DID, DIP, DPort, PrevNAccess)}
  +            PrevNTimers;
  +        [{_, _, _}=DNode|_] ->
  +            del_timer(DNode, PrevNTimers)
       end,
   
   
   
       IsNewMember = b_is_member(ID, IP, Port, NewBuckets),
  -    {NewNTimers, NewNAccess} = case {IsPrevMember, IsNewMember} of
  +    NewNTimers  = case {IsPrevMember, IsNewMember} of
           {false, false} ->
  -            {TmpNTimers, TmpNAccess};
  -
  +            TmpNTimers;
           {true, true} ->
  -            {TmpNTimers, TmpNAccess};
  -        
  -        {false, true} ->
  -            {init_node_timer(ID, IP, Port, NTimeout, TmpNTimers),
  -             init_node_access(ID, IP, Port, TmpNAccess)}
  +            TmpNTimers;
  +        {false, true}  ->
  +            NTimer = node_timer_from(Now, NTimeout, Node),
  +            add_timer(Node, Now, NTimer, TmpNTimers)
       end,
   
       NewBTimers = case {IsPrevMember, IsNewMember} of
           {false, false} ->
  -            % No changes, the old node timers are still valid
               PrevBTimers;
           {true, true} ->
               PrevBTimers;
   
           {false, true} ->
  -            % The bucket set may have changed, The least recently active
  -            % node in the affected buckets may also have changed.
  -            % Reset all bucket timers to be sure.
  -            TmpBTimers = lists:foldl(fun(Range, Acc) ->
  -                cancel_bucket_timer(Range, Acc)
  -            end, PrevBTimers, b_ranges(PrevBuckets)),
  +            AllPrevRanges = b_ranges(PrevBuckets),
  +            AllNewRanges  = b_ranges(NewBuckets),
  +
  +            DelRanges  = subtract(AllPrevRanges, AllNewRanges),
  +            NewRanges  = subtract(AllNewRanges, AllPrevRanges),
  +
  +            DelBTimers = lists:foldl(fun(Range, Acc) ->
  +                del_timer(Range, Acc)
  +            end, PrevBTimers, DelRanges),
               
  -            CaseBTimers = lists:foldl(fun(Range, Acc) ->
  -                TmpBMembers = b_members(Range, NewBuckets),
  -                LeastRecent = n_least_recent(TmpBMembers, NewNAccess),
  -                init_bucket_timer(Range, LeastRecent, BTimeout, Acc)
  -            end, TmpBTimers, b_ranges(NewBuckets)),
  -            CaseBTimers
  +            lists:foldl(fun(Range, Acc) ->
  +                BMembers = b_members(Range, NewBuckets),
  +                LRecent = least_recent(BMembers, NewNTimers),
  +                BTimer = bucket_timer_from(
  +                             Now, BTimeout, LRecent, NTimeout, Range),
  +                add_timer(Range, Now, BTimer, Acc)
  +            end, DelBTimers, NewRanges)
       end, 
  -    B0 = lists:sort(gb_trees:keys(NewBTimers)),
  -    B1 = lists:sort(b_ranges(NewBuckets)),
  -    true = (B0 == B1),
       NewState = State#state{
           buckets=NewBuckets,
           node_timers=NewNTimers,
  -        node_access=NewNAccess,
           buck_timers=NewBTimers},
       {reply, ok, NewState};
               
   
   
   
  -handle_call({closest_to, InputNodeID, NumNodes}, From, State) ->
  +handle_call({closest_to, InputNodeID, NumNodes}, _, State) ->
       NodeID = ensure_int_id(InputNodeID),
       #state{buckets=Buckets} = State,
       Nodes = b_node_list(Buckets),
  
positive.code: -module(etorrent_dht_state).
  -behaviour(gen_server).
  -compile(export_all).
  -import(ordsets, [add_element/2, del_element/2]).
  
  %
  % This module implements a server maintaining the
  
negative.code: %
  b_has_bucket({_, _}, []) ->
      false;
  b_has_bucket({Min, Max}, [{Min, Max, _}|_]) ->
      true;
  b_has_bucket({Min, Max}, [{_, _, _}|T]) ->
      b_has_bucket({Min, Max}, T).
  