code: func (c *FSM) Restore(old io.ReadCloser) error {
  	defer old.Close()
  
  	// Create a new state store.
  	stateNew, err := state.NewStateStore(c.gc)
  	if err != nil {
  		return err
  	}
  
  	// Set up a new restore transaction
  	restore := stateNew.Restore()
  	defer restore.Abort()
  
  	// Create a decoder
  	dec := codec.NewDecoder(old, msgpackHandle)
  
  	// Read in the header
  	var header snapshotHeader
  	if err := dec.Decode(&header); err != nil {
  		return err
  	}
  
  	// Populate the new state
  	msgType := make([]byte, 1)
  	for {
  		// Read the message type
  		_, err := old.Read(msgType)
  		if err == io.EOF {
  			break
  		} else if err != nil {
  			return err
  		}
  
  		// Decode
  		msg := structs.MessageType(msgType[0])
  		if fn := restorers[msg]; fn != nil {
  			if err := fn(&header, restore, dec); err != nil {
  				return err
  			}
  		} else {
  			return fmt.Errorf("Unrecognized msg type %d", msg)
  		}
  	}
  	restore.Commit()
  
  	// External code might be calling State(), so we need to synchronize
  	// here to make sure we swap in the new state store atomically.
  	c.stateLock.Lock()
  	stateOld := c.state
  	c.state = stateNew
  	c.stateLock.Unlock()
  
  	// Signal that the old state store has been abandoned. This is required
  	// because we don't operate on it any more, we just throw it away, so
  	// blocking queries won't see any changes and need to be woken up.
  	stateOld.Abandon()
  	return nil
  }
docs: // Restore streams in the snapshot and replaces the current state store with a
  // new one based on the snapshot if all goes OK during the restore.