Source code for pyGHDL.lsp

# =============================================================================
#               ____ _   _ ____  _       _
#  _ __  _   _ / ___| | | |  _ \| |     | |___ _ __
# | '_ \| | | | |  _| |_| | | | | |     | / __| '_ \
# | |_) | |_| | |_| |  _  | |_| | |___ _| \__ \ |_) |
# | .__/ \__, |\____|_| |_|____/|_____(_)_|___/ .__/
# |_|    |___/                                |_|
# =============================================================================
# Authors:
#   Tristan Gingold
#
# Package module:   Language Server Protocol implementation for VHDL.
#
# License:
# ============================================================================
#  Copyright (C) 2020-2026 Tristan Gingold
#
#  This program is free software: you can redistribute it and/or modify
#  it under the terms of the GNU General Public License as published by
#  the Free Software Foundation, either version 2 of the License, or
#  (at your option) any later version.
#
#  This program is distributed in the hope that it will be useful,
#  but WITHOUT ANY WARRANTY; without even the implied warranty of
#  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
#  GNU General Public License for more details.
#
#  You should have received a copy of the GNU General Public License
#  along with this program.  If not, see <gnu.org/licenses>.
#
# SPDX-License-Identifier: GPL-2.0-or-later
# ============================================================================
"""
Implementation of GHDL's language server.

The package is layered, from the wire upwards:

1. :mod:`pyGHDL.lsp.lsp` speaks the Language Server Protocol over stdin and stdout.
2. :mod:`pyGHDL.lsp.vhdl_ls` implements the VHDL-specific requests on top of it.
3. :mod:`pyGHDL.lsp.workspace` and :mod:`pyGHDL.lsp.document` hold the analyzed sources the requests are answered
   from.

The entry point is :mod:`pyGHDL.cli.lsp`.
"""

from pyTooling.Decorators import export

from pyGHDL import GHDLBaseException


[docs] @export class LSPException(GHDLBaseException): """ The exception is raised for every failure of the language server. It is the base-class of the language server's exceptions, so ``except LSPException`` catches them without also catching failures of the analyzer or of the document object model. """
class LSPConnTrace(object): """Wrapper class to save in and out packets""" def __init__(self, basename, conn): """ Initializes the trace by opening the two log files beside the connection. :param basename: The path the traces are written to, with ``.in`` and ``.out`` appended. :param conn: The connection to wrap. """ self.conn = conn self.trace_in = open(basename + ".in", "w") self.trace_out = open(basename + ".out", "w") def readline(self): """ Read a line from the wrapped connection and record it. :returns: The line that was read. """ res = self.conn.readline() self.trace_in.write(res) return res def read(self, size): """ Read from the wrapped connection and record what was read. :param size: The number of characters to read. :returns: The characters that were read. """ res = self.conn.read(size) self.trace_in.write(res) self.trace_in.flush() return res def write(self, out): """ Write to the wrapped connection and record what was written. :param out: The text to write. """ self.conn.write(out) self.trace_out.write(out) self.trace_out.flush()