Mercurial > hg
view rust/chg/src/clientext.rs @ 44805:02bf61bb4a70
copy: to find copy source, walk parent of revision we're marking copies in
As shown in the previous patch, `hg cp --after --at-rev . src dst`
fails if `src` is not in `.`. It seems obvious that you should always
walk the *parent* of the revision you're marking copies in, but that's
not how it was done for the working copy, and I didn't think to change
it when marking copies in a non-working-copy commit.
This patch fixes that by walking the parent commit instead, but only
if we're marking copies for a non-working-copy commit. We need to
leave the working-copy code unchanged because it depends on the weird
behavior of `workingctx.walk()`. With these changes, there's very
little overlap between the working-copy version and the
non-working-copy version of `walkpats()`, but I've refrained from
cleaning that up on the stable branch.
Differential Revision: https://phab.mercurial-scm.org/D8494
author | Martin von Zweigbergk <martinvonz@google.com> |
---|---|
date | Wed, 06 May 2020 10:33:56 -0700 |
parents | d6f706929120 |
children | 426294d06ddc |
line wrap: on
line source
// Copyright 2018 Yuya Nishihara <yuya@tcha.org> // // This software may be used and distributed according to the terms of the // GNU General Public License version 2 or any later version. //! cHg extensions to command server client. use bytes::{BufMut, BytesMut}; use std::ffi::OsStr; use std::io; use std::mem; use std::os::unix::ffi::OsStrExt; use std::os::unix::io::AsRawFd; use std::path::Path; use tokio_hglib::UnixClient; use crate::attachio; use crate::message::{self, Instruction, ServerSpec}; use crate::runcommand; use crate::uihandler::SystemHandler; /// Command-server client that also supports cHg extensions. pub struct ChgClient { client: UnixClient, } impl ChgClient { /// Connects to a command server listening at the specified socket path. pub async fn connect(path: impl AsRef<Path>) -> io::Result<Self> { let client = UnixClient::connect(path).await?; Ok(ChgClient { client }) } /// Server capabilities, encoding, etc. pub fn server_spec(&self) -> &ServerSpec { self.client.server_spec() } /// Attaches the client file descriptors to the server. pub async fn attach_io( &mut self, stdin: &impl AsRawFd, stdout: &impl AsRawFd, stderr: &impl AsRawFd, ) -> io::Result<()> { attachio::attach_io(self.client.borrow_protocol_mut(), stdin, stdout, stderr).await } /// Changes the working directory of the server. pub async fn set_current_dir(&mut self, dir: impl AsRef<Path>) -> io::Result<()> { let dir_bytes = dir.as_ref().as_os_str().as_bytes().to_owned(); self.client .borrow_protocol_mut() .send_command_with_args("chdir", dir_bytes) .await } /// Updates the environment variables of the server. pub async fn set_env_vars_os( &mut self, vars: impl IntoIterator<Item = (impl AsRef<OsStr>, impl AsRef<OsStr>)>, ) -> io::Result<()> { self.client .borrow_protocol_mut() .send_command_with_args("setenv", message::pack_env_vars_os(vars)) .await } /// Changes the process title of the server. pub async fn set_process_name(&mut self, name: impl AsRef<OsStr>) -> io::Result<()> { let name_bytes = name.as_ref().as_bytes().to_owned(); self.client .borrow_protocol_mut() .send_command_with_args("setprocname", name_bytes) .await } /// Changes the umask of the server process. pub async fn set_umask(&mut self, mask: u32) -> io::Result<()> { let mut mask_bytes = BytesMut::with_capacity(mem::size_of_val(&mask)); mask_bytes.put_u32(mask); self.client .borrow_protocol_mut() .send_command_with_args("setumask2", mask_bytes) .await } /// Runs the specified Mercurial command with cHg extension. pub async fn run_command_chg( &mut self, handler: &mut impl SystemHandler, args: impl IntoIterator<Item = impl AsRef<OsStr>>, ) -> io::Result<i32> { runcommand::run_command( self.client.borrow_protocol_mut(), handler, message::pack_args_os(args), ) .await } /// Validates if the server can run Mercurial commands with the expected /// configuration. /// /// The `args` should contain early command arguments such as `--config` /// and `-R`. /// /// Client-side environment must be sent prior to this request, by /// `set_current_dir()` and `set_env_vars_os()`. pub async fn validate( &mut self, args: impl IntoIterator<Item = impl AsRef<OsStr>>, ) -> io::Result<Vec<Instruction>> { let data = self .client .borrow_protocol_mut() .query_with_args("validate", message::pack_args_os(args)) .await?; message::parse_instructions(data) } }