1####################
2 Visual Studio Code
3####################
4
5.. note::
6
7   These instructions have been tested on Linux. macOS should mostly work the same. For Windows,
8   ymmv.
9
10An IDE can make navigating large code bases tremendously easier. Visual Studio Code is a popular and
11free IDE that is well-suited for C development. It contains syntax highlighting, navigation,
12auto-completion and a debugger. Check the `official website <https://code.visualstudio.com/>`__ for
13installation instructions.
14
15.. note::
16
17   The ``settings.json`` file referenced below can be opened in the Settings page by pressing the
18   "Open Settings (JSON)" button in the top right corner. Most of these settings can also be
19   adjusted through the GUI.
20
21*****************
22 C/C++ extension
23*****************
24
25The `C/C++ extension`_ provides most of the features we'll need for php-src development. You can
26find it in the extensions marketplace. You will also need ``gcc`` or ``clang`` installed. The
27extension will mostly work out of the box, but it is advisable to use the ``compile_commands.json``
28file. It contains a list of all compiled files, along with the commands used to compile them. It
29provides the extension with the necessary information about include paths and other compiler flags.
30
31.. _c/c++ extension: https://marketplace.visualstudio.com/items?itemName=ms-vscode.cpptools
32
33To generate the ``compile_commands.json`` file, you can use the compiledb_ tool. Install it using
34``pip``, and then prefix your ``make`` command accordingly:
35
36.. _compiledb: https://github.com/nickdiego/compiledb
37
38.. code:: bash
39
40   # Install compiledb
41   pip install compiledb
42   # Compile php-src and generate compile_commands.json
43   compiledb make -j8
44
45To tell the C/C++ extension to use the ``compile_commands.json`` file, add the following to your
46``settings.json`` file:
47
48.. code:: json
49
50   {
51       "C_Cpp.default.compileCommands": "${workspaceFolder}/compile_commands.json"
52   }
53
54********
55 clangd
56********
57
58The C/C++ extension usually works well enough. Some people find that ``clangd`` works better.
59``clangd`` is a language server built on top of the ``clang`` compiler. It only provides navigation
60and code completion but no syntax highlighting and no debugger. As such, it should be used in
61conjunction with the C/C++ extension. For the two extensions not to clash, add the following to your
62``settings.json`` file:
63
64.. code:: json
65
66   {
67       "C_Cpp.intelliSenseEngine": "disabled"
68   }
69
70Follow the `official installation instructions for clangd
71<https://clangd.llvm.org/installation.html>`__, and then install the `clangd extension`_.
72Alternatively, you can let the extension install ``clangd`` for you. ``clangd`` requires a
73``compile_commands.json`` file, so make sure to follow the instructions from the previous section.
74By default, ``clangd`` will auto-include header files on completion. php-src headers are somewhat
75peculiar, so you might want to disable this option in your ``settings.json`` file:
76
77.. _clangd extension: https://marketplace.visualstudio.com/items?itemName=llvm-vs-code-extensions.vscode-clangd
78
79.. code:: json
80
81   {
82       "clangd.arguments": [
83           "-header-insertion=never"
84       ]
85   }
86
87*****
88 gdb
89*****
90
91The C/C++ extension provides the ability to use Visual Studio Code as a frontend for ``gdb``. Of
92course, you will need ``gdb`` installed on your system, and php-src must be compiled with the
93``--enable-debug`` configure flag. Copy the following into your projects ``.vscode/launch.json``
94file:
95
96.. code:: json
97
98   {
99       "version": "0.2.0",
100       "configurations": [
101           {
102               "name": "(gdb) Launch",
103               "type": "cppdbg",
104               "request": "launch",
105               "program": "${workspaceFolder}/sapi/cli/php",
106               "args": [
107                   // Any options you want to test with
108                   // "-dopcache.enable_cli=1",
109                   "${relativeFile}",
110               ],
111               "stopAtEntry": false,
112               "cwd": "${workspaceFolder}",
113               // Useful if you build with --enable-address-sanitizer
114               "environment": [
115                   { "name": "USE_ZEND_ALLOC", "value": "0" },
116                   { "name": "USE_TRACKED_ALLOC", "value": "1" },
117                   { "name": "LSAN_OPTIONS", "value": "detect_leaks=0" },
118               ],
119               "externalConsole": false,
120               "MIMode": "gdb",
121               "setupCommands": [
122                   { "text": "source ${workspaceFolder}/.gdbinit" },
123               ]
124           }
125       ]
126   }
127
128Set any breakpoint in your C code, open a ``php`` (or ``phpt``) file and start debugging from the
129"Run and Debug" tab in the sidebar.
130
131..
132   _todo: lldb should work mostly the same, I believe. It's available by default on macOS, and as such might be more convenient.
133