QMTANHVNRPQ5IX66FYQBFRBDCTN6YKMNCO6OHTQ6QCUASPWWXJKAC GHO6DWPILBBTL6CVZKERJBTFL3EY6ZT4YM4E5R4S6YPGVFKFHCVAC 3KRGVQFUWFHPOGZOXVTJYNCM4XBRVYITAEOVPKBSAZ5GZIUO5KVQC SXEYMYF7P4RZMZ46WPL4IZUTSQ2ATBWYZX7QNVMS3SGOYXYOHAGQC L4JXJHWXYNCL4QGJXNKKTOKKTAXKKXBJUUY7HFZGEUZ5A2V5H34QC I52XSRUH5RVHQBFWVMAQPTUSPAJ4KNVID2RMI3UGCVKFLYUO6WZAC WZVCLZKY34KQBQU6YBGJLQCDADBQ67LQVDNRVCMQVY3O3C3EIWSQC VQPAUKBQ2POZKL7CZFAZK5ZQKEBYL27XZYZWYUSH5AH25KK6DWKAC CCLLB7OIFNFYJZTG3UCI7536TOCWSCSXR67VELSB466R24WLJSDAC 76PCXGML77EZWTRI5E6KHLVRAFTJ2AB5YRN5EKOYNAPKTWY2KCGAC if !overwrite_changes {// No need to change channel, no need to reset.return Ok(());
if overwrite_changes {txn.output_repository_no_pending(&mut repo.working_copy,&repo.changes,&mut channel,&mut HashMap::new(),"",true,)?;txn.commit()?;
txn.output_repository_no_pending(&mut repo.working_copy,&repo.changes,&mut channel,&mut HashMap::new(),"",true,)?;
let mut inodes = HashSet::new();if let Some(cur) = txn.load_channel(current_channel)? {let mut changediff = HashSet::new();let (a, b, s) = libpijul::pristine::last_common_state(&txn,&cur.borrow(),&channel.borrow(),)?;debug!("last common state {:?}", s);changes_after(&txn, &cur.borrow(), a, &mut changediff, &mut inodes)?;changes_after(&txn, &channel.borrow(), b, &mut changediff, &mut inodes)?;}if self.channel.is_some() {repo.config.current_channel = self.channel;repo.save_config()?;}for pos in inodes.iter() {let (path, _) = libpijul::fs::find_path(&repo.changes,&txn,&channel.borrow(),false,*pos,)?;debug!("resetting {:?}", path);txn.output_repository_no_pending(&mut repo.working_copy,&repo.changes,&mut channel,&mut HashMap::new(),&path,true,)?;}
}}fn changes_after<T: ChannelTxnT + DepsTxnT>(txn: &T,chan: &T::Channel,from: u64,changediff: &mut HashSet<ChangeId>,inodes: &mut HashSet<Position<ChangeId>>,) -> Result<(), anyhow::Error> {for x in libpijul::pristine::changeid_log(txn, chan, from)? {let (n, (u, _)) = x?;debug!("{:?} {:?} {:?}", n, u, from);if n <= from {continue;}if changediff.insert(u) {for y in txn.iter_rev_touched_files(u, None)? {let (uu, pos) = y?;if uu < u {continue;} else if uu > u {break;}inodes.insert(pos);}}
}fn first_state_after<T: ChannelTxnT>(txn: &T, c: &T::Channel, pos: u64) -> Result<Option<(u64, Merkle)>, TxnErr<T::GraphError>> {for x in T::cursor_revchangeset_ref(txn, T::rev_changes(&c), Some(pos))? {let (n, (_, m)) = x?;if n >= pos {return Ok(Some((n, m)))}}Ok(None)}fn last_state<T: ChannelTxnT>(txn: &T, c: &T::Channel) -> Result<Option<(u64, Merkle)>, TxnErr<T::GraphError>> {if let Some(e) = txn.rev_cursor_revchangeset(T::rev_changes(&c), None)?.next(){let (b, (_, state)) = e?;Ok(Some((b, state)))} else {Ok(None)}}/// Find the last state of c1 that is also in c0.pub fn last_common_state<T: ChannelTxnT>(txn: &T, c0: &T::Channel, c1: &T::Channel) -> Result<(u64, u64, Merkle), TxnErr<T::GraphError>> {let mut a = 0;let (mut b, mut state) = if let Some(x) = last_state(txn, c1)? {x} else {return Ok((0, 0, Merkle::zero()))};if let Some(aa) = txn.channel_has_state(c0, state)? {return Ok((aa, b, state))}let mut aa = 0;while a < b {let mid = (a+b) / 2;let (_, s) = first_state_after(txn, c1, mid)?.unwrap();state = s;if let Some(aa_) = txn.channel_has_state(c0, state)? {aa = aa_;a = mid} else {b = mid}}Ok((aa, a, state))