UNPKG

@imc-trading/svlangserver

Version:
321 lines (293 loc) 13.1 kB
# SVLangserver A language server for systemverilog that has been tested to work with coc.nvim, VSCode, Sublime Text 4 and emacs ## Features - Auto completion (no need for ctags or other such mechanisms) - Go to symbol in document - Go to symbol in workspace folder (indexed modules/interfaces/packages) - Go to definition (_works for module/interface/package names and for ports too!_) - Hover over help - Signature help - Fast indexing - Verilator/Icarus linting on the fly - Report hierarchy of a module - Code snippets for many common blocks - Code formatting with verible-verilog-format - Elaborate syntax highlighting (for VSCode) ## Versions The code has been tested to work with below tool versions - vim 8.2 * coc.nvim 0.0.80-0b5130ea38 - VSCode 1.52.0 - Sublime Text Build 4126 - emacs 29.0.50 * lsp-mode lsp-mode-20220328.1429 - Neovim 0.7.0 - Verilator 4.110 - Icarus Verilog Compiler 10.2 - Verible v0.0-1114-ged89c1b ## Installation - For coc.nvim * `npm install -g @imc-trading/svlangserver` * Update .vim/coc-settings.json - For VSCode * Install the extension from the marketplace. * Update the settings - For Sublime Text 3 * Install the systemverilog package in sublime text * `npm install -g @imc-trading/svlangserver` * Update the LSP settings (`Preferences -> Package Settings -> LSP -> settings`) and the sublime-project files - For emacs * Install lsp-mode * `npm install -g @imc-trading/svlangserver` * Update .emacs/init.el - For neovim * Install [nvim-lspconfig](https://github.com/neovim/nvim-lspconfig) * `npm install -g @imc-trading/svlangserver` * Add following setting in your init.lua ```lua require'lspconfig'.svlangserver.setup{} ``` * Update .nvim/lspconfig.json To get the snippets, git clone this repo and copy the snippets directory wherever applicable For installing from source (not applicable for VSCode) - `git clone https://github.com/imc-trading/svlangserver.git` - `cd svlangserver && npm install` * Update the settings with the correct command (e.g. `/git/repo/path/svlangserver/bin/main.js`) NOTE: This has been tested with npm version 6.14.13 and node version 14.17.1 ## Settings - `systemverilog.includeIndexing`: _Array_, Globs defining files to be indexed - `systemverilog.libraryIndexing`: _Array_, Globs defining library files to be added to linting. It's useful when module name is not equal to filename. - `systemverilog.excludeIndexing`: _Array_, Exclude files from indexing based on glob - `systemverilog.linter`: _String_, Select linter * Default: _'verilator'_ - `systemverilog.launchConfiguration`: _String_, Command to run for launching linting * Default: _verilator --sv --lint-only --Wall_ * If not in path, replace _verilator_ with the appropriate command - `systemverilog.lintOnUnsaved`: _Boolean_, Lint even unsaved files * Default: _true_ - `systemverilog.defines`: _Array_, Defines for the project. Used by the language server as well as linting * Default: _empty_ - `systemverilog.formatCommand`: _String_, verible-verilog-format command for code formatting * Default: _verible-verilog-format_ * If not in path, replace _verible-verilog-format_ with the appropriate command - `systemverilog.disableCompletionProvider`: _Boolean_, Disable auto completion provided by the language server * Default: _false_ - `systemverilog.disableHoverProvider`: _Boolean_, Disable hover over help provided by the language server * Default: _false_ - `systemverilog.disableSignatureHelpProvider`: _Boolean_, Disable signature help provided by the language server * Default: _false_ - `systemverilog.disableLinting`: _Boolean_, Disable linting * Default: _false_ - Example coc.nvim settings file ```json { "languageserver": { "svlangserver": { "command": "svlangserver", "filetypes": ["systemverilog"], "settings": { "systemverilog.includeIndexing": ["**/*.{sv,svh}"], "systemverilog.excludeIndexing": ["test/**/*.sv*"], "systemverilog.defines" : [], "systemverilog.launchConfiguration": "/tools/verilator -sv -Wall --lint-only", "systemverilog.formatCommand": "/tools/verible-verilog-format" } } } } ``` For project specific settings this file should be at `<WORKSPACE PATH>/.vim/coc-settings.json` - Example coc.nvim settings file (for windows) ```json { "languageserver": { "svlangserver": { "module": "/usr/lib/node_modules/@imc-trading/svlangserver/bin/main.js", "args": ["--node-ipc"], "filetypes": ["systemverilog"], "settings": { "systemverilog.includeIndexing": ["**/*.{sv,svh}"], "systemverilog.excludeIndexing": ["test/**/*.sv*"], "systemverilog.defines" : [], "systemverilog.launchConfiguration": "/tools/verilator -sv -Wall --lint-only", "systemverilog.formatCommand": "/tools/verible-verilog-format" } } } } ``` For project specific settings this file should be at `<WORKSPACE PATH>\.vim\coc-settings.json` - Example vscode settings file ```json { "systemverilog.includeIndexing": ["**/*.{sv,svh}"], "systemverilog.excludeIndexing": ["test/**/*.sv*"], "systemverilog.defines" : [], "systemverilog.launchConfiguration": "/tools/verilator -sv -Wall --lint-only", "systemverilog.formatCommand": "/tools/verible-verilog-format" } ``` For project specific settings this file should be at `<WORKSPACE PATH>/.vscode/settings.json` - Example Sublime Text 3 settings files * The global LSP settings file: LSP.sublime-settings ```json { "clients": { "svlangserver": { "enabled": true, "command": ["svlangserver"], "languageId": "systemverilog", "scopes": ["source.systemverilog"], "syntaxes": ["Packages/SystemVerilog/SystemVerilog.sublime-syntax"], "settings": { "systemverilog.disableHoverProvider": true, "systemverilog.launchConfiguration": "/tools/verilator -sv --lint-only -Wall", "systemverilog.formatCommand" : "/tools/verible-verilog-format" } } } } ``` * The project specific settings go in `<PROJECT>.sublime-project` ```json { "folders": [ { "path": "." } ], "settings": { "LSP": { "svlangserver": { "settings": { "systemverilog.includeIndexing": [ "**/*.{sv,svh}", ], "systemverilog.excludeIndexing": ["test/**/*.sv*"], "systemverilog.defines": [], } } } } } ``` - Example settings for emacs * Below content goes in .emacs or init.el ```elisp (require 'lsp-verilog) (custom-set-variables '(lsp-clients-svlangserver-launchConfiguration "/tools/verilator -sv --lint-only -Wall") '(lsp-clients-svlangserver-formatCommand "/tools/verible-verilog-format")) (add-hook 'verilog-mode-hook #'lsp-deferred) ``` * The project specific settings go in .dir-locals.el ```elisp ((verilog-mode (lsp-clients-svlangserver-workspace-additional-dirs . ("/some/lib/path")) (lsp-clients-svlangserver-includeIndexing . ("src/**/*.{sv,svh}")) (lsp-clients-svlangserver-excludeIndexing . ("src/test/**/*.{sv,svh}")))) ``` - Example neovim settings file ```json { "languageserver": { "svlangserver": { "command": "svlangserver", "filetypes": ["systemverilog"], "settings": { "systemverilog.includeIndexing": ["**/*.{sv,svh}"], "systemverilog.excludeIndexing": ["test/**/*.sv*"], "systemverilog.defines" : [], "systemverilog.launchConfiguration": "/tools/verilator -sv -Wall --lint-only", "systemverilog.formatCommand": "/tools/verible-verilog-format" } } } } ``` For project specific settings this file should be at `<WORKSPACE PATH>/.nvim/lspconfig.json` ## Commands * `systemverilog.build_index`: Instructs language server to rerun indexing * `systemverilog.report_hierarchy`: Generates hierarchy for the given module ### coc.nvim usage * The commands should be executed using CocRequest function. An example vim command would be: ```vim command! SvBuildIndex call CocRequest("svlangserver", 'workspace/executeCommand', {'command': 'systemverilog.build_index'}) command! -range SvReportHierarchy call CocRequest("svlangserver", 'workspace/executeCommand', {'command': 'systemverilog.report_hierarchy', 'arguments': [input('Module/interface: ', <range> == 0 ? "" : expand("<cword>"))]}) ``` If the above SvReportHierarchy command is called with visual selection, then the module name is pre-filled with the selection. Also depending on the coc.nvim version, the generated rpt.json file might not have the focus and user will have to switch buffer manually. ### VSCode usage * Typing `build index` in the command palette should invoke the build index command. * Typing `get hierarchy` in the command palette should invoke the report hierarchy command. If invoked with an active slection, the module name is pre-filled with the selection. ### Sublime usage * A sublime-commands file needs to be created with the below content ```json [ { "caption": "SvLangserver Build Index", "command": "lsp_execute", "args": { "session_name": "svlangserver", "command_name": "systemverilog.build_index", "command_args": [] } }, { "caption": "Svlangserver Report Hierarchy", "command": "lsp_execute", "args": { "session_name": "svlangserver", "command_name": "systemverilog.report_hierarchy", "command_args": ["${selection}"] } } ] ``` This should make the commands available in the command palette. For the report hierarchy command, the module name should be selected before invoking the command. ### Emacs usage * `lsp-clients-svlangserver-build-index` command should rerun the indexing. * `lsp-clients-svlangserver-report-hierarchy` command should do the job. If invoked with an active slection, the module name is pre-filled with the selection. ### Neovim usage * `:SvlangserverBuildIndex` command should rerun the indexing. * `:SvlangserverReportHierarchy` command will generate hierarchy file of the word under the cursor in normal mode. ## Troubleshooting - Editor is not able to find language server binary. * Make sure the binary is in the system path as exposed to the editor. If the binary is installed in custom directory, expose that path to your editor - Not getting any diagnostics * Make sure the launchConfiguration setting has been properly set to use verilator from the correct installation path - Diagnostics show _Cannot find file containing module 'module_name'_ * Make sure all submodules can be found by includeIndexing * If the issue still remains, it may due to different naming of module and file, or a file containing multiple modules. Make sure these files can be found by libraryIndexing. - Check settings used by the language server * for coc.nvim: Use the command `:CocCommand workspace.showOutput` and then select svlangserver * for vscode: Check the SVLangServer output channel * for sublime: Open the command palette in the tools menu and select `LSP: Toggle Log Panel` * for emacs: Check the `*lsp-log*` buffer * for neovim: Add `vim.lsp.set_log_level("info")` in your init.lua then check ~/.cache/nvim/lsp.log ## Known Issues - Language server doesn't understand most verification specific concepts (e.g. classes). ## Future Rewrite parser to make it much more robust ## Acknowledgements Although most of the code is written from scratch, this [VSCode-SystemVerilog extension](https://github.com/eirikpre/VSCode-SystemVerilog/) was what I started with and developed on. ## Release Notes See the [changelog](CHANGELOG.md) for more details ### 0.4.1 - Support for Neovim client with nvim-lspconfig - Updated settings for faster indexing - Bug fixes ### 0.4.0 - Icarus as linting alternative - Command for reporting hierarchy - Improved hover over formatting - Improved symbol resolution - Bug fixes ### 0.3.5 - Improvements to auto-completion and jump to definition - Bug fixes ### 0.3.4 - Bug fixes ### 0.3.3 - Updated instructions to use published packages ### 0.3.1 - Add support for Sublime LSP and Emacs ### 0.3.0 - Initial release