[lint] Add tool version check for Veriblelint

Signed-off-by: Michael Schaffner <msf@opentitan.org>
diff --git a/azure-pipelines.yml b/azure-pipelines.yml
index 410f17c..5e75dd8 100644
--- a/azure-pipelines.yml
+++ b/azure-pipelines.yml
@@ -40,15 +40,6 @@
     displayName: Remove existing Clang installation
   - template: ci/install-package-dependencies.yml
   - bash: |
-      set -e
-      mkdir -p build/verible
-      cd build/verible
-      curl -Ls -o verible.tar.gz "https://github.com/google/verible/releases/download/$(VERIBLE_VERSION)/verible-$(VERIBLE_VERSION)-Ubuntu-$(lsb_release -sr)-$(lsb_release -sc)-x86_64.tar.gz"
-      sudo mkdir -p /tools/verible && sudo chmod 777 /tools/verible
-      tar -C /tools/verible -xf verible.tar.gz --strip-components=1
-      echo "##vso[task.setvariable variable=PATH]/tools/verible/bin:$PATH"
-    displayName: Install Verible
-  - bash: |
       set -x
       python3 --version
       yapf --version
@@ -58,6 +49,7 @@
       ninja --version
       meson --version
       doxygen --version
+      verible-verilog-lint --version
       echo "PATH=$PATH"
       printenv
     displayName: Display environment information
@@ -332,6 +324,7 @@
       python3 --version
       fusesoc --version
       verilator --version
+      verible-verilog-lint --version
     displayName: Display environment
   - bash: |
       . util/build_consts.sh
diff --git a/check_tool_requirements.core b/check_tool_requirements.core
index 375970c..1ace868 100644
--- a/check_tool_requirements.core
+++ b/check_tool_requirements.core
@@ -28,4 +28,5 @@
       - files_check_tool_requirements
     hooks:
       pre_build:
-        - tool_verilator ? (check_tool_requirements)
+        - tool_verilator   ? (check_tool_requirements)
+        - tool_veriblelint ? (check_tool_requirements)
diff --git a/ci/install-package-dependencies.yml b/ci/install-package-dependencies.yml
index 66615b9..0cfbc85 100644
--- a/ci/install-package-dependencies.yml
+++ b/ci/install-package-dependencies.yml
@@ -66,6 +66,13 @@
 
       pip3 install --user -U -r python-requirements.txt
 
+      # Install Verible
+      mkdir -p build/verible
+      cd build/verible
+      curl -Ls -o verible.tar.gz "https://github.com/google/verible/releases/download/$(VERIBLE_VERSION)/verible-$(VERIBLE_VERSION)-Ubuntu-$(lsb_release -sr)-$(lsb_release -sc)-x86_64.tar.gz"
+      sudo mkdir -p /tools/verible && sudo chmod 777 /tools/verible
+      tar -C /tools/verible -xf verible.tar.gz --strip-components=1
+
       # Propagate PATH changes to all subsequent steps of the job
-      echo "##vso[task.setvariable variable=PATH]$PATH"
+      echo "##vso[task.setvariable variable=PATH]/tools/verible/bin:$PATH"
     displayName: 'Install package dependencies'
diff --git a/doc/ug/install_instructions/index.md b/doc/ug/install_instructions/index.md
index c390d1e..1aa910f 100644
--- a/doc/ug/install_instructions/index.md
+++ b/doc/ug/install_instructions/index.md
@@ -260,11 +260,11 @@
 ```console
 $ export VERIBLE_VERSION={{< tool_version "verible" >}}
 
-$ wget https://github.com/google/verible/releases/download/v${VERIBLE_VERSION}/verible-v${VERIBLE_VERSION}-Ubuntu-18.04-bionic-x86_64.tar.gz
-$ tar -xf verible-v${VERIBLE_VERSION}-Ubuntu-18.04-bionic-x86_64.tar.gz
+$ wget https://github.com/google/verible/releases/download/v${VERIBLE_VERSION}/verible-${VERIBLE_VERSION}-Ubuntu-18.04-bionic-x86_64.tar.gz
+$ tar -xf verible-${VERIBLE_VERSION}-Ubuntu-18.04-bionic-x86_64.tar.gz
 
 $ sudo mkdir -p /tools/verible/${VERIBLE_VERSION}/
-$ sudo mv verible-v${VERIBLE_VERSION}/* /tools/verible/${VERIBLE_VERSION}/
+$ sudo mv verible-${VERIBLE_VERSION}/* /tools/verible/${VERIBLE_VERSION}/
 ```
 
 After installation you need to add `/tools/verible/$VERIBLE_VERSION/bin` to your `PATH` environment variable.
diff --git a/tool_requirements.py b/tool_requirements.py
index 175a7de..9f9a799 100644
--- a/tool_requirements.py
+++ b/tool_requirements.py
@@ -8,6 +8,6 @@
     'edalize': '0.2.0',
     'hugo_extended': '0.71.0',
     'ninja-build': '1.8.2',
-    'verible': '0.0-808-g1e17daa',
+    'verible': 'v0.0-808-g1e17daa',
     'verilator': '4.104',
 }
diff --git a/util/check_tool_requirements.py b/util/check_tool_requirements.py
index 3c6757d..2e46ed1 100755
--- a/util/check_tool_requirements.py
+++ b/util/check_tool_requirements.py
@@ -68,6 +68,35 @@
         return None
 
 
+def convert_verible_version(version_string):
+    '''Convert Verible version string to semantic versioning format.'''
+    # Drop the hash suffix and convert into version string that
+    # is compatible with StrictVersion in check_version below.
+    # Example: v0.0-808-g1e17daa -> 0.0.808
+    m = re.fullmatch(r'v([0-9]+)\.([0-9]+)-([0-9]+)-g[0-9a-f]+$', version_string)
+
+    if m is None:
+        log.error("{} has invalid version string format.".format(version_string))
+        return None
+
+    return '.'.join(m.group(1, 2, 3))
+
+
+def get_verible_version():
+    '''Run Verible to check its version'''
+    try:
+        version_str = subprocess.run('verible-verilog-lint --version', shell=True,
+                                     check=True, stdout=subprocess.PIPE,
+                                     stderr=subprocess.STDOUT,
+                                     universal_newlines=True)
+        return version_str.stdout.split('\n')[0].strip()
+
+    except subprocess.CalledProcessError as e:
+        log.error("Unable to call Verible to check version: " + str(e))
+        log.error(e.stdout)
+        return None
+
+
 def pip3_get_version(tool):
     '''Run pip3 to find the version of an installed module'''
     cmd = ['pip3', 'show', tool]
@@ -96,7 +125,7 @@
     return None
 
 
-def check_version(requirements, tool_name, getter):
+def check_version(requirements, tool_name, getter, version_converter=None):
     required_version = requirements.get(tool_name)
     if required_version is None:
         log.error('Requirements file does not specify version for {}.'
@@ -107,6 +136,12 @@
     if actual_version is None:
         return False
 
+    # If a version string converter is defined, call it. This is required
+    # for some version strings that are not compatible with StrictVersion.
+    if version_converter is not None:
+        required_version = version_converter(required_version)
+        actual_version = version_converter(actual_version)
+
     if StrictVersion(actual_version) < StrictVersion(required_version):
         log.error("%s is too old: found version %s, need at least %s",
                   tool_name, actual_version, required_version)
@@ -128,6 +163,10 @@
                               'verilator',
                               get_verilator_version)
     all_good &= check_version(tool_requirements,
+                              'verible',
+                              get_verible_version,
+                              convert_verible_version)
+    all_good &= check_version(tool_requirements,
                               'edalize',
                               lambda: pip3_get_version('edalize'))