forked from chipsalliance/verible
-
Notifications
You must be signed in to change notification settings - Fork 2
/
verible-verilog-format-changed-lines-interactive.sh
executable file
·175 lines (153 loc) · 5.34 KB
/
verible-verilog-format-changed-lines-interactive.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
#!/usr/bin/env bash
# verible-verilog-format-changed-lines-interactive.sh.
# Copyright 2020 The Verible Authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
script_name="$(basename $0)"
script_dir="$(dirname $0)"
# Look first for support scripts/binaries installed alongside this script.
# Fall back to searching in current PATH.
# This is the script that drives interactive patching.
interactive_patch_script="$script_dir"/verible-transform-interactive.sh
[[ -x "$interactive_patch_script" ]] || \
interactive_patch_script="$(which verible-transform-interactive.sh)"
# This is Verible's patch-based utility.
patch_tool="$script_dir"/verible-patch-tool
[[ -x "$patch_tool" ]] || patch_tool="$(which verible-patch-tool)"
# This is Verible's Verilog formatter.
formatter="$script_dir"/verible-verilog-format
[[ -x "$formatter" ]] || formatter="$(which verible-verilog-format)"
# version control system
# auto-detect by default
rcs=auto
baserev=
files=()
function usage() {
cat <<EOF
$0:
Interactively prompts user to accept/reject formatter tool changes,
based only on touched lines of code in a revision-controlled workspace.
Usage: $script_name [script_options] [FILES...]
Run this from a version-controlled directory.
If FILES is empty, scan for all Verilog files under the current directory.
script options:
--help, -h : print help and exit
--rcs TOOL : revision control system [default:$rcs]
Supported: p4,git,hg
--base REV : Revision to diff against [default: git:HEAD hg:.]
See tool-specific help for version specifiers:
git help revisions
hg help revisions
EOF
}
function msg() {
echo "[$script_name] " "$@"
}
# generic option processing
for opt
do
# handle: --option arg
if test -n "$prev_opt"
then
eval $prev_opt=\$opt
prev_opt=
shift
continue
fi
case "$opt" in
*=?*) optarg=$(expr "X$opt" : '[^=]*=\(.*\)') ;;
*=) optarg= ;;
esac
case $opt in
-- ) shift ; break ;; # stop option processing
--help | -h ) { usage ; exit ;} ;;
--rcs ) prev_opt=rcs ;;
--rcs=* ) rcs="$optarg" ;;
--base ) prev_opt=baserev ;;
--base=* ) baserev="$optarg" ;;
--* | -* ) msg "Unknown option: $opt" ; exit 1 ;;
# Positional arguments [optional] are files.
*) files+=( "$opt" ) ;;
esac
shift
done
# attempt to infer version control system (p4,svn,git,cvs,hg,...)
# Note: these tests are sensitive to "$PWD"
if [[ "$rcs" == "auto" ]]
then
if git status
then
rcs=git
elif hg root
then
rcs=hg
else
# p4 is tricky to detect due to the concept of default clients,
# so leave it last position, if all else fails.
rcs=p4
fi > /dev/null 2>&1
fi
# Set default rev to 'dot' (parent) or HEAD. User can override
# to a different revision if they want (eg p4head)
case "$rcs" in
git) baserev=${baserev:-HEAD} ;;
hg) baserev=${baserev:-.} ;;
esac
function p4_touched_files() {
# Result is already absolute paths to local files.
p4 whatsout
}
function git_touched_files() {
# Get added/modified files that are tracked.
# See git help diff.
# readlink: resolve absolute path to eliminate sensitivity to "$PWD"
# Since 'git status' doesn't allow passing in a revision, use git diff instead
# of status. But that gives a root-relative path, so cd to the root first
(cd $(git rev-parse --show-toplevel) ;
git diff --name-only --diff-filter=AM "$baserev" | xargs readlink -f
)
}
function hg_touched_files() {
# Get added/modified files that are tracked.
# See hg help status
hg status --no-status -am --rev "$baserev" | xargs readlink -f
}
# Set commands based on version control system
case "$rcs" in
p4) touched_files=p4_touched_files
# force use of traditional text 'diff', not some other UI-diff tool
single_file_diff=(P4DIFF=diff p4 diff -d-u "{}") ;;
git) touched_files=git_touched_files
single_file_diff=(git diff -u --cached "$baserev" "{}") ;;
hg) touched_files=hg_touched_files
single_file_diff=(hg diff -g --rev "$baserev" "{}") ;;
*) { msg "Unsupported version control system: $rcs" ; exit 1;} ;;
esac
# If files is unspecified, scan for all locally modified files.
if [[ "${#files[@]}" == 0 ]]
then
# File extensions are currently hardcoded to Verilog files.
files=($("$touched_files" | grep -e '\.sv$' -e '\.v$' -e '\.svh$' -e '\.vh$' ))
fi
# Note about --per-file-transform-flags:
# The file name is stripped away to yield only line numbers, which is why
# this still works with git-diffs, which contain a/ and b/ prefixes in
# filenames. The file name used for applying changes is still the one from
# "${files[@]}".
interact_command=("$interactive_patch_script" \
--patch-tool "$patch_tool" \
--per-file-transform-flags='--lines=$('"${single_file_diff[*]}"' | '"$patch_tool"' changed-lines - | cut -d" " -f2)' \
-- "$formatter" \
-- "${files[@]}" )
msg "interact command: ${interact_command[@]}"
exec "${interact_command[@]}"