Mercurial > hg
comparison rust/hg-core/src/revlog/index.rs @ 51261:9088c6d65ef6
rust-index-cpython: cache the heads' PyList representation
This is the same optimization that the C index does, we just have more
separation of the Python and native sides.
author | Raphaël Gomès <rgomes@octobus.net> |
---|---|
date | Wed, 29 Nov 2023 23:22:51 -0500 |
parents | c4f1a790bda8 |
children | 47a34afda7ad |
comparison
equal
deleted
inserted
replaced
51260:c4f1a790bda8 | 51261:9088c6d65ef6 |
---|---|
542 } | 542 } |
543 } | 543 } |
544 | 544 |
545 /// Return the head revisions of this index | 545 /// Return the head revisions of this index |
546 pub fn head_revs(&self) -> Result<Vec<Revision>, GraphError> { | 546 pub fn head_revs(&self) -> Result<Vec<Revision>, GraphError> { |
547 self.head_revs_filtered(&HashSet::new()) | 547 self.head_revs_filtered(&HashSet::new(), false) |
548 .map(|h| h.unwrap()) | |
549 } | |
550 | |
551 /// Python-specific shortcut to save on PyList creation | |
552 pub fn head_revs_shortcut( | |
553 &self, | |
554 ) -> Result<Option<Vec<Revision>>, GraphError> { | |
555 self.head_revs_filtered(&HashSet::new(), true) | |
548 } | 556 } |
549 | 557 |
550 /// Return the head revisions of this index | 558 /// Return the head revisions of this index |
551 pub fn head_revs_filtered( | 559 pub fn head_revs_filtered( |
552 &self, | 560 &self, |
553 filtered_revs: &HashSet<Revision>, | 561 filtered_revs: &HashSet<Revision>, |
554 ) -> Result<Vec<Revision>, GraphError> { | 562 py_shortcut: bool, |
563 ) -> Result<Option<Vec<Revision>>, GraphError> { | |
555 { | 564 { |
556 let guard = self | 565 let guard = self |
557 .head_revs | 566 .head_revs |
558 .read() | 567 .read() |
559 .expect("RwLock on Index.head_revs should not be poisoned"); | 568 .expect("RwLock on Index.head_revs should not be poisoned"); |
560 let self_head_revs = &guard.0; | 569 let self_head_revs = &guard.0; |
561 let self_filtered_revs = &guard.1; | 570 let self_filtered_revs = &guard.1; |
562 if !self_head_revs.is_empty() | 571 if !self_head_revs.is_empty() |
563 && filtered_revs == self_filtered_revs | 572 && filtered_revs == self_filtered_revs |
564 { | 573 { |
565 return Ok(self_head_revs.to_owned()); | 574 if py_shortcut { |
575 // Don't copy the revs since we've already cached them | |
576 // on the Python side. | |
577 return Ok(None); | |
578 } else { | |
579 return Ok(Some(self_head_revs.to_owned())); | |
580 } | |
566 } | 581 } |
567 } | 582 } |
568 | 583 |
569 let as_vec = if self.is_empty() { | 584 let as_vec = if self.is_empty() { |
570 vec![NULL_REVISION] | 585 vec![NULL_REVISION] |
590 *self | 605 *self |
591 .head_revs | 606 .head_revs |
592 .write() | 607 .write() |
593 .expect("RwLock on Index.head_revs should not be poisoned") = | 608 .expect("RwLock on Index.head_revs should not be poisoned") = |
594 (as_vec.to_owned(), filtered_revs.to_owned()); | 609 (as_vec.to_owned(), filtered_revs.to_owned()); |
595 Ok(as_vec) | 610 Ok(Some(as_vec)) |
596 } | 611 } |
597 | 612 |
598 /// Obtain the delta chain for a revision. | 613 /// Obtain the delta chain for a revision. |
599 /// | 614 /// |
600 /// `stop_rev` specifies a revision to stop at. If not specified, we | 615 /// `stop_rev` specifies a revision to stop at. If not specified, we |