code: func (c *RegionCache) GetRPCContext(bo *Backoffer, id RegionVerID) (*RPCContext, error) {
  	c.mu.RLock()
  	region := c.getCachedRegion(id)
  	if region == nil {
  		c.mu.RUnlock()
  		return nil, nil
  	}
  	// Note: it is safe to use region.meta and region.peer without clone after
  	// unlock, because region cache will never update the content of region's meta
  	// or peer. On the contrary, if we want to use `region` after unlock, then we
  	// need to clone it to avoid data race.
  	meta, peer := region.meta, region.peer
  	c.mu.RUnlock()
  
  	addr, err := c.GetStoreAddr(bo, peer.GetStoreId())
  	if err != nil {
  		return nil, errors.Trace(err)
  	}
  	if addr == "" {
  		// Store not found, region must be out of date.
  		c.DropRegion(id)
  		return nil, nil
  	}
  	return &RPCContext{
  		Region: id,
  		Meta:   meta,
  		Peer:   peer,
  		Addr:   addr,
  	}, nil
  }
docs: // GetRPCContext returns RPCContext for a region. If it returns nil, the region
  // must be out of date and already dropped from cache.