Coverage for tsfpga/vivado/common.py: 73%
48 statements
« prev ^ index » next coverage.py v6.5.0, created at 2023-01-31 20:01 +0000
« prev ^ index » next coverage.py v6.5.0, created at 2023-01-31 20:01 +0000
1# --------------------------------------------------------------------------------------------------
2# Copyright (c) Lukas Vik. All rights reserved.
3#
4# This file is part of the tsfpga project, a project platform for modern FPGA development.
5# https://tsfpga.com
6# https://gitlab.com/tsfpga/tsfpga
7# --------------------------------------------------------------------------------------------------
9# Standard libraries
10from pathlib import Path
11from shutil import which
13# Third party libraries
14from vunit.ostools import Process
16# First party libraries
17from tsfpga.git_utils import get_git_sha
18from tsfpga.math_utils import to_binary_string
21def run_vivado_tcl(vivado_path, tcl_file, no_log_file=False):
22 """
23 Setting cwd ensures that any .log or .jou files produced are placed in
24 the same directory as the TCL file that produced them.
26 Arguments:
27 vivado_path (pathlib.Path): Path to Vivado executable. Can set to ``None``
28 to use whatever version is in ``PATH``.
29 tcl_file (pathlib.Path): Path to TCL file.
31 Return:
32 bool: True if everything went well.
33 """
34 tcl_file = tcl_file.resolve()
36 cmd = [
37 str(get_vivado_path(vivado_path)),
38 "-mode",
39 "batch",
40 "-notrace",
41 "-source",
42 str(tcl_file),
43 ]
44 if no_log_file:
45 cmd += ["-nojournal", "-nolog"]
47 try:
48 Process(args=cmd, cwd=tcl_file.parent).consume_output()
49 except Process.NonZeroExitCode:
50 return False
51 return True
54def run_vivado_gui(vivado_path, project_file):
55 """
56 Setting cwd ensures that any .log or .jou files produced are placed in
57 the same directory as the project.
59 Arguments:
60 vivado_path (pathlib.Path): Path to Vivado executable. Can set to ``None``
61 to use whatever version is in ``PATH``.
62 project_file (pathlib.Path): Path to a project .xpr file.
64 Return:
65 bool: True if everything went well.
66 """
67 project_file = project_file.resolve()
68 if not project_file.exists():
69 raise FileNotFoundError(f"Project does not exist: {project_file}")
71 cmd = [str(get_vivado_path(vivado_path)), "-mode", "gui", str(project_file)]
73 try:
74 Process(args=cmd, cwd=project_file.parent).consume_output()
75 except Process.NonZeroExitCode:
76 return False
77 return True
80def get_vivado_path(vivado_path=None):
81 """
82 Wrapper to get a path to Vivado executable.
84 Arguments:
85 vivado_path (pathlib.Path): Path to vivado executable. Set to ``None`` to use whatever
86 is available in the system ``PATH``.
88 Returns:
89 pathlib.Path: The path.
90 """
91 if vivado_path is not None:
92 return vivado_path.resolve()
94 which_vivado = which("vivado")
95 if which_vivado is None:
96 raise FileNotFoundError("Could not find vivado on PATH")
98 return Path(which_vivado).resolve()
101def get_vivado_version(vivado_path=None):
102 """
103 Get the version number of the Vivado installation.
105 Arguments:
106 vivado_path (pathlib.Path): Path to vivado executable. Set to ``None`` to use whatever
107 is available in the system ``PATH``.
109 Returns:
110 str: The version, e.g. ``"2021.2"``.
111 """
112 vivado_path = get_vivado_path(vivado_path=vivado_path)
114 # E.g. "/home/lukas/work/Xilinx/Vivado/2021.2/bin/vivado" -> "2021.2"
115 vivado_version = vivado_path.parent.parent.name
117 return vivado_version
120def get_git_sha_slv(git_directory):
121 """
122 Get the current git SHA encoded as 32-character binary strings. Suitable for setting
123 as ``std_logic_vector`` generics to a Vivado build, where they can be assigned to
124 software-accessible registers to keep track of what revision an FPGA was built from.
126 Will return the left-most 16 characters of the git SHA, encoded into two 32-character strings.
128 Arguments:
129 directory (pathlib.Path): The directory where git commands will be run.
131 Returns:
132 tuple(str, str): First object in tuple is the left-most eight characters of the git SHA
133 encoded as a 32-character binary string. Second object is the next eight characters from
134 the git SHA.
135 """
136 git_sha = get_git_sha(directory=git_directory)
137 assert len(git_sha) == 16
139 def hex_to_binary_string(hex_string):
140 assert len(hex_string) == 8
141 int_value = int(hex_string, base=16)
143 return to_binary_string(int_value=int_value, result_width=32)
145 left_binary_string = hex_to_binary_string(hex_string=git_sha[0:8])
146 right_binary_string = hex_to_binary_string(hex_string=git_sha[8:16])
148 return (left_binary_string, right_binary_string)
151def to_tcl_path(path):
152 """
153 Return a path string in a format suitable for TCL.
154 """
155 return str(path.resolve()).replace("\\", "/")