annotate rust/rhg/src/commands/status.rs @ 49517:52464a20add0

rhg: parallellize computation of [unsure_is_modified] [unsure_is_modified] is called for every file for which we can't determine its status based on its size and mtime alone. In particular, this happens if the mtime of the file changes without its contents changing. Parallellizing this improves performance significantly when we have many of these files. Here's an example run (on a repo with ~400k files after dropping FS caches) ``` before: real 0m53.901s user 0m27.806s sys 0m31.325s after: real 0m32.017s user 0m34.277s sys 1m26.250s ``` Another example run (a different FS): ``` before: real 3m28.479s user 0m31.800s sys 0m25.324s after: real 0m29.751s user 0m41.814s sys 1m15.387s ```
author Arseniy Alekseyev <aalekseyev@janestreet.com>
date Wed, 05 Oct 2022 15:45:05 -0400
parents 3854eb90629b
children 37bc3edef76f baa4e2c93642
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
1 // status.rs
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
2 //
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
3 // Copyright 2020, Georges Racinet <georges.racinets@octobus.net>
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
4 //
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
5 // This software may be used and distributed according to the terms of the
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
6 // GNU General Public License version 2 or any later version.
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
7
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
8 use crate::error::CommandError;
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
9 use crate::ui::Ui;
48453
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
10 use crate::utils::path_utils::RelativizePaths;
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
11 use clap::{Arg, SubCommand};
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
12 use format_bytes::format_bytes;
48175
707c58880cd0 rhg: add relative paths support in `rhg status`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 48171
diff changeset
13 use hg::config::Config;
48391
b80e5e75d51e dirstate: remove `lastnormaltime` mechanism
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 48349
diff changeset
14 use hg::dirstate::has_exec_bit;
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
15 use hg::dirstate::status::StatusPath;
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
16 use hg::dirstate::TruncatedTimestamp;
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
17 use hg::errors::{HgError, IoResultExt};
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
18 use hg::lock::LockError;
47964
796206e74b10 rhg: Reuse manifest when checking status of multiple ambiguous files
Simon Sapin <simon.sapin@octobus.net>
parents: 47956
diff changeset
19 use hg::manifest::Manifest;
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
20 use hg::matchers::{AlwaysMatcher, IntersectionMatcher};
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
21 use hg::repo::Repo;
48345
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
22 use hg::utils::files::get_bytes_from_os_string;
48511
c9abfb80b4e3 rhg: Properly format warnings related to ignore patterns
Simon Sapin <simon.sapin@octobus.net>
parents: 48501
diff changeset
23 use hg::utils::files::get_bytes_from_path;
48451
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
24 use hg::utils::files::get_path_from_bytes;
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
25 use hg::utils::hg_path::{hg_path_to_path_buf, HgPath};
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
26 use hg::DirstateStatus;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
27 use hg::PatternFileWarning;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
28 use hg::StatusError;
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
29 use hg::StatusOptions;
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
30 use hg::{self, narrow, sparse};
48511
c9abfb80b4e3 rhg: Properly format warnings related to ignore patterns
Simon Sapin <simon.sapin@octobus.net>
parents: 48501
diff changeset
31 use log::info;
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
32 use rayon::prelude::*;
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
33 use std::io;
48451
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
34 use std::path::PathBuf;
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
35
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
36 pub const HELP_TEXT: &str = "
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
37 Show changed files in the working directory
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
38
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
39 This is a pure Rust version of `hg status`.
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
40
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
41 Some options might be missing, check the list below.
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
42 ";
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
43
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
44 pub fn args() -> clap::App<'static, 'static> {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
45 SubCommand::with_name("status")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
46 .alias("st")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
47 .about(HELP_TEXT)
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
48 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
49 Arg::with_name("all")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
50 .help("show status of all files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
51 .short("-A")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
52 .long("--all"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
53 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
54 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
55 Arg::with_name("modified")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
56 .help("show only modified files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
57 .short("-m")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
58 .long("--modified"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
59 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
60 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
61 Arg::with_name("added")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
62 .help("show only added files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
63 .short("-a")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
64 .long("--added"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
65 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
66 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
67 Arg::with_name("removed")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
68 .help("show only removed files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
69 .short("-r")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
70 .long("--removed"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
71 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
72 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
73 Arg::with_name("clean")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
74 .help("show only clean files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
75 .short("-c")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
76 .long("--clean"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
77 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
78 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
79 Arg::with_name("deleted")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
80 .help("show only deleted files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
81 .short("-d")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
82 .long("--deleted"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
83 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
84 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
85 Arg::with_name("unknown")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
86 .help("show only unknown (not tracked) files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
87 .short("-u")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
88 .long("--unknown"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
89 )
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
90 .arg(
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
91 Arg::with_name("ignored")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
92 .help("show only ignored files")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
93 .short("-i")
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
94 .long("--ignored"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
95 )
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
96 .arg(
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
97 Arg::with_name("copies")
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
98 .help("show source of copied files (DEFAULT: ui.statuscopies)")
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
99 .short("-C")
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
100 .long("--copies"),
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
101 )
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
102 .arg(
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
103 Arg::with_name("no-status")
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
104 .help("hide status prefix")
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
105 .short("-n")
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
106 .long("--no-status"),
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
107 )
49439
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
108 .arg(
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
109 Arg::with_name("verbose")
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
110 .help("enable additional output")
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
111 .short("-v")
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
112 .long("--verbose"),
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
113 )
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
114 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
115
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
116 /// Pure data type allowing the caller to specify file states to display
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
117 #[derive(Copy, Clone, Debug)]
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
118 pub struct DisplayStates {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
119 pub modified: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
120 pub added: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
121 pub removed: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
122 pub clean: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
123 pub deleted: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
124 pub unknown: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
125 pub ignored: bool,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
126 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
127
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
128 pub const DEFAULT_DISPLAY_STATES: DisplayStates = DisplayStates {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
129 modified: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
130 added: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
131 removed: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
132 clean: false,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
133 deleted: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
134 unknown: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
135 ignored: false,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
136 };
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
137
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
138 pub const ALL_DISPLAY_STATES: DisplayStates = DisplayStates {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
139 modified: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
140 added: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
141 removed: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
142 clean: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
143 deleted: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
144 unknown: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
145 ignored: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
146 };
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
147
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
148 impl DisplayStates {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
149 pub fn is_empty(&self) -> bool {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
150 !(self.modified
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
151 || self.added
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
152 || self.removed
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
153 || self.clean
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
154 || self.deleted
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
155 || self.unknown
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
156 || self.ignored)
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
157 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
158 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
159
49439
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
160 fn has_unfinished_merge(repo: &Repo) -> Result<bool, CommandError> {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
161 return Ok(repo.dirstate_parents()?.is_merge());
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
162 }
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
163
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
164 fn has_unfinished_state(repo: &Repo) -> Result<bool, CommandError> {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
165 // These are all the known values for the [fname] argument of
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
166 // [addunfinished] function in [state.py]
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
167 let known_state_files: &[&str] = &[
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
168 "bisect.state",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
169 "graftstate",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
170 "histedit-state",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
171 "rebasestate",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
172 "shelvedstate",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
173 "transplant/journal",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
174 "updatestate",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
175 ];
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
176 if has_unfinished_merge(repo)? {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
177 return Ok(true);
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
178 };
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
179 for f in known_state_files {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
180 if repo.hg_vfs().join(f).exists() {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
181 return Ok(true);
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
182 }
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
183 }
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
184 return Ok(false);
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
185 }
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
186
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
187 pub fn run(invocation: &crate::CliInvocation) -> Result<(), CommandError> {
48171
64b8676f11bb rhg: fallback if tweakdefaults or statuscopies is enabled with status
Pulkit Goyal <7895pulkit@gmail.com>
parents: 48069
diff changeset
188 // TODO: lift these limitations
48338
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
189 if invocation
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
190 .config
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
191 .get(b"commands", b"status.terse")
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
192 .is_some()
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
193 {
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
194 return Err(CommandError::unsupported(
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
195 "status.terse is not yet supported with rhg status",
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
196 ));
f9db8eeb3aec rhg: Config commands.status.terse is not supported
Simon Sapin <simon.sapin@octobus.net>
parents: 48337
diff changeset
197 }
48171
64b8676f11bb rhg: fallback if tweakdefaults or statuscopies is enabled with status
Pulkit Goyal <7895pulkit@gmail.com>
parents: 48069
diff changeset
198
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
199 let ui = invocation.ui;
48175
707c58880cd0 rhg: add relative paths support in `rhg status`
Pulkit Goyal <7895pulkit@gmail.com>
parents: 48171
diff changeset
200 let config = invocation.config;
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
201 let args = invocation.subcommand_args;
48513
47f2a82ae3e4 rhg: Fall back to Python if verbose status is requested by config
Simon Sapin <simon.sapin@octobus.net>
parents: 48511
diff changeset
202
49512
6939d5ed20e0 rhg: central treatment of PLAIN and PLAINEXCEPT
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49489
diff changeset
203 let verbose = !args.is_present("print0")
49439
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
204 && (args.is_present("verbose")
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
205 || config.get_bool(b"ui", b"verbose")?
48513
47f2a82ae3e4 rhg: Fall back to Python if verbose status is requested by config
Simon Sapin <simon.sapin@octobus.net>
parents: 48511
diff changeset
206 || config.get_bool(b"commands", b"status.verbose")?);
47f2a82ae3e4 rhg: Fall back to Python if verbose status is requested by config
Simon Sapin <simon.sapin@octobus.net>
parents: 48511
diff changeset
207
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
208 let all = args.is_present("all");
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
209 let display_states = if all {
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
210 // TODO when implementing `--quiet`: it excludes clean files
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
211 // from `--all`
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
212 ALL_DISPLAY_STATES
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
213 } else {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
214 let requested = DisplayStates {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
215 modified: args.is_present("modified"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
216 added: args.is_present("added"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
217 removed: args.is_present("removed"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
218 clean: args.is_present("clean"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
219 deleted: args.is_present("deleted"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
220 unknown: args.is_present("unknown"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
221 ignored: args.is_present("ignored"),
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
222 };
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
223 if requested.is_empty() {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
224 DEFAULT_DISPLAY_STATES
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
225 } else {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
226 requested
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
227 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
228 };
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
229 let no_status = args.is_present("no-status");
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
230 let list_copies = all
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
231 || args.is_present("copies")
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
232 || config.get_bool(b"ui", b"statuscopies")?;
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
233
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
234 let repo = invocation.repo?;
48409
005ae1a343f8 rhg: add support for narrow clones and sparse checkouts
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 48391
diff changeset
235
49439
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
236 if verbose {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
237 if has_unfinished_state(repo)? {
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
238 return Err(CommandError::unsupported(
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
239 "verbose status output is not supported by rhg (and is needed because we're in an unfinished operation)",
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
240 ));
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
241 };
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
242 }
b07465adbcc8 rhg: make [rhg status -v] work when it needs no extra output
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49374
diff changeset
243
47956
81aedf1fc897 rust: Add Repo::dirstate_map and use it in `rhg status`
Simon Sapin <simon.sapin@octobus.net>
parents: 47682
diff changeset
244 let mut dmap = repo.dirstate_map_mut()?;
47674
ff97e793ed36 dirstate-v2: Introduce a docket file
Simon Sapin <simon.sapin@octobus.net>
parents: 47374
diff changeset
245
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
246 let options = StatusOptions {
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
247 // we're currently supporting file systems with exec flags only
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
248 // anyway
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
249 check_exec: true,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
250 list_clean: display_states.clean,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
251 list_unknown: display_states.unknown,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
252 list_ignored: display_states.ignored,
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
253 list_copies,
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
254 collect_traversed_dirs: false,
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
255 };
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
256
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
257 type StatusResult<'a> =
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
258 Result<(DirstateStatus<'a>, Vec<PatternFileWarning>), StatusError>;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
259
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
260 let after_status = |res: StatusResult| -> Result<_, CommandError> {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
261 let (mut ds_status, pattern_warnings) = res?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
262 for warning in pattern_warnings {
49483
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
263 ui.write_stderr(&print_pattern_file_warning(&warning, &repo))?;
48511
c9abfb80b4e3 rhg: Properly format warnings related to ignore patterns
Simon Sapin <simon.sapin@octobus.net>
parents: 48501
diff changeset
264 }
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
265
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
266 for (path, error) in ds_status.bad {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
267 let error = match error {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
268 hg::BadMatch::OsError(code) => {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
269 std::io::Error::from_raw_os_error(code).to_string()
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
270 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
271 hg::BadMatch::BadType(ty) => {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
272 format!("unsupported file type (type is {})", ty)
47321
62225f9da938 rhg: Sort `rhg status` output correctly
Simon Sapin <simon.sapin@octobus.net>
parents: 47110
diff changeset
273 }
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
274 };
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
275 ui.write_stderr(&format_bytes!(
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
276 b"{}: {}\n",
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
277 path.as_bytes(),
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
278 error.as_bytes()
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
279 ))?
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
280 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
281 if !ds_status.unsure.is_empty() {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
282 info!(
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
283 "Files to be rechecked by retrieval from filelog: {:?}",
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
284 ds_status.unsure.iter().map(|s| &s.path).collect::<Vec<_>>()
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
285 );
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
286 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
287 let mut fixup = Vec::new();
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
288 if !ds_status.unsure.is_empty()
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
289 && (display_states.modified || display_states.clean)
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
290 {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
291 let p1 = repo.dirstate_parents()?.p1;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
292 let manifest = repo.manifest_for_node(p1).map_err(|e| {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
293 CommandError::from((e, &*format!("{:x}", p1.short())))
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
294 })?;
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
295 let working_directory_vfs = repo.working_directory_vfs();
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
296 let store_vfs = repo.store_vfs();
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
297 let res: Vec<_> = ds_status
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
298 .unsure
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
299 .into_par_iter()
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
300 .map(|to_check| {
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
301 unsure_is_modified(
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
302 working_directory_vfs,
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
303 store_vfs,
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
304 &manifest,
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
305 &to_check.path,
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
306 )
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
307 .map(|modified| (to_check, modified))
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
308 })
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
309 .collect::<Result<_, _>>()?;
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
310 for (status_path, is_modified) in res.into_iter() {
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
311 if is_modified {
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
312 if display_states.modified {
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
313 ds_status.modified.push(status_path);
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
314 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
315 } else {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
316 if display_states.clean {
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
317 ds_status.clean.push(status_path.clone());
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
318 }
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
319 fixup.push(status_path.path.into_owned())
47321
62225f9da938 rhg: Sort `rhg status` output correctly
Simon Sapin <simon.sapin@octobus.net>
parents: 47110
diff changeset
320 }
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
321 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
322 }
49512
6939d5ed20e0 rhg: central treatment of PLAIN and PLAINEXCEPT
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49489
diff changeset
323 let relative_paths = config
6939d5ed20e0 rhg: central treatment of PLAIN and PLAINEXCEPT
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49489
diff changeset
324 .get_option(b"commands", b"status.relative")?
6939d5ed20e0 rhg: central treatment of PLAIN and PLAINEXCEPT
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49489
diff changeset
325 .unwrap_or(config.get_bool(b"ui", b"relative-paths")?);
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
326 let output = DisplayStatusPaths {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
327 ui,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
328 no_status,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
329 relativize: if relative_paths {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
330 Some(RelativizePaths::new(repo)?)
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
331 } else {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
332 None
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
333 },
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
334 };
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
335 if display_states.modified {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
336 output.display(b"M ", "status.modified", ds_status.modified)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
337 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
338 if display_states.added {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
339 output.display(b"A ", "status.added", ds_status.added)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
340 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
341 if display_states.removed {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
342 output.display(b"R ", "status.removed", ds_status.removed)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
343 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
344 if display_states.deleted {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
345 output.display(b"! ", "status.deleted", ds_status.deleted)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
346 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
347 if display_states.unknown {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
348 output.display(b"? ", "status.unknown", ds_status.unknown)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
349 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
350 if display_states.ignored {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
351 output.display(b"I ", "status.ignored", ds_status.ignored)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
352 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
353 if display_states.clean {
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
354 output.display(b"C ", "status.clean", ds_status.clean)?;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
355 }
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
356
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
357 let dirstate_write_needed = ds_status.dirty;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
358 let filesystem_time_at_status_start =
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
359 ds_status.filesystem_time_at_status_start;
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
360
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
361 Ok((
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
362 fixup,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
363 dirstate_write_needed,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
364 filesystem_time_at_status_start,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
365 ))
48452
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
366 };
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
367 let (narrow_matcher, narrow_warnings) = narrow::matcher(repo)?;
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
368 let (sparse_matcher, sparse_warnings) = sparse::matcher(repo)?;
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
369 let matcher = match (repo.has_narrow(), repo.has_sparse()) {
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
370 (true, true) => {
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
371 Box::new(IntersectionMatcher::new(narrow_matcher, sparse_matcher))
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
372 }
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
373 (true, false) => narrow_matcher,
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
374 (false, true) => sparse_matcher,
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
375 (false, false) => Box::new(AlwaysMatcher),
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
376 };
49485
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
377
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
378 for warning in narrow_warnings.into_iter().chain(sparse_warnings) {
49485
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
379 match &warning {
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
380 sparse::SparseWarning::RootWarning { context, line } => {
49485
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
381 let msg = format_bytes!(
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
382 b"warning: {} profile cannot use paths \"
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
383 starting with /, ignoring {}\n",
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
384 context,
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
385 line
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
386 );
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
387 ui.write_stderr(&msg)?;
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
388 }
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
389 sparse::SparseWarning::ProfileNotFound { profile, rev } => {
49485
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
390 let msg = format_bytes!(
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
391 b"warning: sparse profile '{}' not found \"
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
392 in rev {} - ignoring it\n",
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
393 profile,
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
394 rev
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
395 );
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
396 ui.write_stderr(&msg)?;
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
397 }
49489
7c93e38a0bbd rhg-status: add support for narrow clones
Raphaël Gomès <rgomes@octobus.net>
parents: 49485
diff changeset
398 sparse::SparseWarning::Pattern(e) => {
49485
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
399 ui.write_stderr(&print_pattern_file_warning(e, &repo))?;
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
400 }
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
401 }
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
402 }
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
403 let (fixup, mut dirstate_write_needed, filesystem_time_at_status_start) =
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
404 dmap.with_status(
49485
ffd4b1f1c9cb rhg: add sparse support
Raphaël Gomès <rgomes@octobus.net>
parents: 49483
diff changeset
405 matcher.as_ref(),
49000
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
406 repo.working_directory_path().to_owned(),
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
407 ignore_files(repo, config),
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
408 options,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
409 after_status,
dd6b67d5c256 rust: fix unsound `OwningDirstateMap`
Raphaël Gomès <rgomes@octobus.net>
parents: 48738
diff changeset
410 )?;
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
411
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
412 if (fixup.is_empty() || filesystem_time_at_status_start.is_none())
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
413 && !dirstate_write_needed
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
414 {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
415 // Nothing to update
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
416 return Ok(());
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
417 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
418
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
419 // Update the dirstate on disk if we can
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
420 let with_lock_result =
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
421 repo.try_with_wlock_no_wait(|| -> Result<(), CommandError> {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
422 if let Some(mtime_boundary) = filesystem_time_at_status_start {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
423 for hg_path in fixup {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
424 use std::os::unix::fs::MetadataExt;
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
425 let fs_path = hg_path_to_path_buf(&hg_path)
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
426 .expect("HgPath conversion");
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
427 // Specifically do not reuse `fs_metadata` from
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
428 // `unsure_is_clean` which was needed before reading
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
429 // contents. Here we access metadata again after reading
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
430 // content, in case it changed in the meantime.
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
431 let fs_metadata = repo
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
432 .working_directory_vfs()
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
433 .symlink_metadata(&fs_path)?;
48443
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
434 if let Some(mtime) =
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
435 TruncatedTimestamp::for_reliable_mtime_of(
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
436 &fs_metadata,
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
437 &mtime_boundary,
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
438 )
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
439 .when_reading_file(&fs_path)?
112184713852 rhg: Set second_ambiguous as needed in post-status fixup
Simon Sapin <simon.sapin@octobus.net>
parents: 48422
diff changeset
440 {
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
441 let mode = fs_metadata.mode();
49110
4d3f6767319f rhg: use the new `set_clean` API
Raphaël Gomès <rgomes@octobus.net>
parents: 49000
diff changeset
442 let size = fs_metadata.len();
4d3f6767319f rhg: use the new `set_clean` API
Raphaël Gomès <rgomes@octobus.net>
parents: 49000
diff changeset
443 dmap.set_clean(&hg_path, mode, size as u32, mtime)?;
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
444 dirstate_write_needed = true
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
445 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
446 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
447 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
448 drop(dmap); // Avoid "already mutably borrowed" RefCell panics
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
449 if dirstate_write_needed {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
450 repo.write_dirstate()?
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
451 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
452 Ok(())
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
453 });
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
454 match with_lock_result {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
455 Ok(closure_result) => closure_result?,
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
456 Err(LockError::AlreadyHeld) => {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
457 // Not updating the dirstate is not ideal but not critical:
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
458 // don’t keep our caller waiting until some other Mercurial
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
459 // process releases the lock.
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
460 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
461 Err(LockError::Other(HgError::IoError { error, .. }))
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
462 if error.kind() == io::ErrorKind::PermissionDenied =>
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
463 {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
464 // `hg status` on a read-only repository is fine
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
465 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
466 Err(LockError::Other(error)) => {
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
467 // Report other I/O errors
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
468 Err(error)?
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
469 }
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
470 }
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
471 Ok(())
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
472 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
473
48451
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
474 fn ignore_files(repo: &Repo, config: &Config) -> Vec<PathBuf> {
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
475 let mut ignore_files = Vec::new();
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
476 let repo_ignore = repo.working_directory_vfs().join(".hgignore");
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
477 if repo_ignore.exists() {
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
478 ignore_files.push(repo_ignore)
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
479 }
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
480 for (key, value) in config.iter_section(b"ui") {
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
481 if key == b"ignore" || key.starts_with(b"ignore.") {
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
482 let path = get_path_from_bytes(value);
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
483 // TODO: expand "~/" and environment variable here, like Python
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
484 // does with `os.path.expanduser` and `os.path.expandvars`
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
485
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
486 let joined = repo.working_directory_path().join(path);
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
487 ignore_files.push(joined);
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
488 }
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
489 }
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
490 ignore_files
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
491 }
4a983b69e519 rhg: Add support for ui.ignore and ui.ignore.* config
Simon Sapin <simon.sapin@octobus.net>
parents: 48443
diff changeset
492
48452
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
493 struct DisplayStatusPaths<'a> {
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
494 ui: &'a Ui,
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
495 no_status: bool,
48453
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
496 relativize: Option<RelativizePaths>,
48452
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
497 }
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
498
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
499 impl DisplayStatusPaths<'_> {
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
500 // Probably more elegant to use a Deref or Borrow trait rather than
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
501 // harcode HgPathBuf, but probably not really useful at this point
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
502 fn display(
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
503 &self,
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
504 status_prefix: &[u8],
48734
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
505 label: &'static str,
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
506 mut paths: Vec<StatusPath<'_>>,
48452
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
507 ) -> Result<(), CommandError> {
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
508 paths.sort_unstable();
48738
00efd2d5037d rust: fix code formatting
Simon Sapin <simon.sapin@octobus.net>
parents: 48735
diff changeset
509 // TODO: get the stdout lock once for the whole loop
00efd2d5037d rust: fix code formatting
Simon Sapin <simon.sapin@octobus.net>
parents: 48735
diff changeset
510 // instead of in each write
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
511 for StatusPath { path, copy_source } in paths {
48453
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
512 let relative;
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
513 let path = if let Some(relativize) = &self.relativize {
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
514 relative = relativize.relativize(&path);
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
515 &*relative
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
516 } else {
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
517 path.as_bytes()
9b0e1f64656f rhg: refactor relativize_path into a struct + method
Simon Sapin <simon.sapin@octobus.net>
parents: 48452
diff changeset
518 };
48734
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
519 // TODO: Add a way to use `write_bytes!` instead of `format_bytes!`
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
520 // in order to stream to stdout instead of allocating an
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
521 // itermediate `Vec<u8>`.
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
522 if !self.no_status {
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
523 self.ui.write_stdout_labelled(status_prefix, label)?
48452
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
524 }
48734
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
525 self.ui
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
526 .write_stdout_labelled(&format_bytes!(b"{}\n", path), label)?;
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
527 if let Some(source) = copy_source {
48734
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
528 let label = "status.copied";
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
529 self.ui.write_stdout_labelled(
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
530 &format_bytes!(b" {}\n", source.as_bytes()),
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
531 label,
3e2b4bb286e7 rhg: Colorize `rhg status` output when appropriate
Simon Sapin <simon.sapin@octobus.net>
parents: 48729
diff changeset
532 )?
48454
473af5cbc209 rhg: Add support for `rhg status --copies`
Simon Sapin <simon.sapin@octobus.net>
parents: 48453
diff changeset
533 }
48349
c12ed33558cb rhg: Add support for `rhg status -n`
Simon Sapin <simon.sapin@octobus.net>
parents: 48345
diff changeset
534 }
48452
2afaa0145584 rhg: refactor display_status_paths with a struct for common arguments
Simon Sapin <simon.sapin@octobus.net>
parents: 48451
diff changeset
535 Ok(())
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
536 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
537 }
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
538
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
539 /// Check if a file is modified by comparing actual repo store and file system.
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
540 ///
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
541 /// This meant to be used for those that the dirstate cannot resolve, due
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
542 /// to time resolution limits.
48344
b6d8eea9872c rhg: Rename cat_file_is_modified
Simon Sapin <simon.sapin@octobus.net>
parents: 48343
diff changeset
543 fn unsure_is_modified(
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
544 working_directory_vfs: hg::vfs::Vfs,
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
545 store_vfs: hg::vfs::Vfs,
47964
796206e74b10 rhg: Reuse manifest when checking status of multiple ambiguous files
Simon Sapin <simon.sapin@octobus.net>
parents: 47956
diff changeset
546 manifest: &Manifest,
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
547 hg_path: &HgPath,
47964
796206e74b10 rhg: Reuse manifest when checking status of multiple ambiguous files
Simon Sapin <simon.sapin@octobus.net>
parents: 47956
diff changeset
548 ) -> Result<bool, HgError> {
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
549 let vfs = working_directory_vfs;
48422
000130cfafb6 rhg: Update the dirstate on disk after status
Simon Sapin <simon.sapin@octobus.net>
parents: 48409
diff changeset
550 let fs_path = hg_path_to_path_buf(hg_path).expect("HgPath conversion");
48345
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
551 let fs_metadata = vfs.symlink_metadata(&fs_path)?;
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
552 let is_symlink = fs_metadata.file_type().is_symlink();
48391
b80e5e75d51e dirstate: remove `lastnormaltime` mechanism
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 48349
diff changeset
553 // TODO: Also account for `FALLBACK_SYMLINK` and `FALLBACK_EXEC` from the
b80e5e75d51e dirstate: remove `lastnormaltime` mechanism
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 48349
diff changeset
554 // dirstate
48345
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
555 let fs_flags = if is_symlink {
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
556 Some(b'l')
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
557 } else if has_exec_bit(&fs_metadata) {
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
558 Some(b'x')
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
559 } else {
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
560 None
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
561 };
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
562
48343
eb428010aad2 rhg: Also parse flags in the manifest parser
Simon Sapin <simon.sapin@octobus.net>
parents: 48342
diff changeset
563 let entry = manifest
48495
e293ff808a05 rhg: Use binary search in manifest lookup
Simon Sapin <simon.sapin@octobus.net>
parents: 48471
diff changeset
564 .find_by_path(hg_path)?
47964
796206e74b10 rhg: Reuse manifest when checking status of multiple ambiguous files
Simon Sapin <simon.sapin@octobus.net>
parents: 47956
diff changeset
565 .expect("ambgious file not in p1");
48345
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
566 if entry.flags != fs_flags {
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
567 return Ok(true);
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
568 }
49517
52464a20add0 rhg: parallellize computation of [unsure_is_modified]
Arseniy Alekseyev <aalekseyev@janestreet.com>
parents: 49516
diff changeset
569 let filelog = hg::filelog::Filelog::open_vfs(&store_vfs, hg_path)?;
48471
b005d07ded7d rhg: Skip reading the contents of ambiguous files in some cases
Simon Sapin <simon.sapin@octobus.net>
parents: 48467
diff changeset
570 let fs_len = fs_metadata.len();
49374
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
571 let file_node = entry.node_id()?;
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
572 let filelog_entry = filelog.entry_for_node(file_node).map_err(|_| {
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
573 HgError::corrupted(format!(
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
574 "filelog missing node {:?} from manifest",
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
575 file_node
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
576 ))
455fce57e89e rust: don't swallow valuable error information
Raphaël Gomès <rgomes@octobus.net>
parents: 49110
diff changeset
577 })?;
48546
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
578 if filelog_entry.file_data_len_not_equal_to(fs_len) {
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
579 // No need to read file contents:
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
580 // it cannot be equal if it has a different length.
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
581 return Ok(true);
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
582 }
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
583
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
584 let p1_filelog_data = filelog_entry.data()?;
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
585 let p1_contents = p1_filelog_data.file_data()?;
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
586 if p1_contents.len() as u64 != fs_len {
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
587 // No need to read file contents:
48471
b005d07ded7d rhg: Skip reading the contents of ambiguous files in some cases
Simon Sapin <simon.sapin@octobus.net>
parents: 48467
diff changeset
588 // it cannot be equal if it has a different length.
b005d07ded7d rhg: Skip reading the contents of ambiguous files in some cases
Simon Sapin <simon.sapin@octobus.net>
parents: 48467
diff changeset
589 return Ok(true);
b005d07ded7d rhg: Skip reading the contents of ambiguous files in some cases
Simon Sapin <simon.sapin@octobus.net>
parents: 48467
diff changeset
590 }
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
591
48345
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
592 let fs_contents = if is_symlink {
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
593 get_bytes_from_os_string(vfs.read_link(fs_path)?.into_os_string())
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
594 } else {
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
595 vfs.read(fs_path)?
d5a91701f7dc rhg: Fix status desambiguation of symlinks and executable files
Simon Sapin <simon.sapin@octobus.net>
parents: 48344
diff changeset
596 };
48546
e91aa800ae5b rhg: desambiguate status without decompressing filelog if possible
Simon Sapin <simon.sapin@octobus.net>
parents: 48542
diff changeset
597 Ok(p1_contents != &*fs_contents)
46822
c71e8d9e7f2a rhg: Initial support for the 'status' command
Georges Racinet <georges.racinet@octobus.net>
parents:
diff changeset
598 }
49483
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
599
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
600 fn print_pattern_file_warning(
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
601 warning: &PatternFileWarning,
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
602 repo: &Repo,
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
603 ) -> Vec<u8> {
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
604 match warning {
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
605 PatternFileWarning::InvalidSyntax(path, syntax) => format_bytes!(
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
606 b"{}: ignoring invalid syntax '{}'\n",
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
607 get_bytes_from_path(path),
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
608 &*syntax
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
609 ),
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
610 PatternFileWarning::NoSuchFile(path) => {
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
611 let path = if let Ok(relative) =
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
612 path.strip_prefix(repo.working_directory_path())
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
613 {
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
614 relative
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
615 } else {
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
616 &*path
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
617 };
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
618 format_bytes!(
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
619 b"skipping unreadable pattern file '{}': \
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
620 No such file or directory\n",
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
621 get_bytes_from_path(path),
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
622 )
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
623 }
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
624 }
b18e877ea304 rhg-status: extract a function for printing pattern file warnings
Raphaël Gomès <rgomes@octobus.net>
parents: 49439
diff changeset
625 }