ocaml-lsp icon indicating copy to clipboard operation
ocaml-lsp copied to clipboard

Memory Leak

Open Nima-Rahimi-Foroushaani opened this issue 2 years ago • 2 comments

It seems ocamllsp has a memory leak. It works fine with my projects and ml files unless for a specific ml file after I added some code, ocamllsp started to allocate memory until the system runs out of memory and ocamllsp gets restarted. If I checkout my file to previous version then ocamllsp works fine again. Even if I open just the file and not the project ocamllsp starts to allocate all the system memory. Apparently, my code triggers the bug/leak. The ml file is this.

I reproduced the bug with the same source code file and following setups.

OS: Ubuntu 20.04.4 LTS VSCode: 1.70.0 Ocaml Platform: 1.10.7 switch & ocamllsp: 4.11.2 & 1.4.1 / 4.14.0 & 1.13.1

OS: macOS 12.0.1 VSCode: 1.70.0 Ocaml Platform: 1.10.7 switch & ocamllsp: 4.12.0 & 1.7.0

Attached are the ocamllsp logs I have got from the first setup before the system kills ocamllsp process 1_sw_4_14_0_lsp_1_13_1.txt 2_sw_4_14_0_lsp_1_13_1.txt 3_sw_4_14_0_lsp_1_13_1.txt

Nima-Rahimi-Foroushaani avatar Aug 11 '22 12:08 Nima-Rahimi-Foroushaani

PS: to continue coding I tried to use merlin (4.2-411 and 4.6-414) instead. The same scenario of consuming all system memory happens for ocamlmerlin-server.

Nima-Rahimi-Foroushaani avatar Aug 12 '22 13:08 Nima-Rahimi-Foroushaani

@voodoos would you be interested in having a look?

ulugbekna avatar Aug 12 '22 14:08 ulugbekna

Could you try reproducing this issue with the most recent version of LSP? The version you're currently using is far too old and we're afraid we cannot fix any issues with it.

rgrinberg avatar Aug 17 '22 18:08 rgrinberg

@rgrinberg As I have mentioned I had the issue with ocamllsp 1.13.1 which is the latest release based on ocaml-lsp github repo. Do you mean the latest trunk by the most recent version?

Nima-Rahimi-Foroushaani avatar Aug 18 '22 09:08 Nima-Rahimi-Foroushaani

Okay, thanks. I misunderstood.

rgrinberg avatar Aug 18 '22 16:08 rgrinberg

I wasn't able to reproduce. Do I need to build the project to reproduce this issue? I don't see any dune files.

rgrinberg avatar Aug 18 '22 17:08 rgrinberg

@voodoos would you be interested in having a look?

I think I am able to reproduce: when opening the specified file, even with no configuration the extension helper slows everything down.

I think it is linked to the outline command that is very slow in that case: Running ocamlmerlin single outline -filename vf_mir_translator.ml <vf_mir_translator.ml takes 11 seconds on my machine and outputs 300mb of text. The memory usage tops at 1.8go which is a lot but not infinitely growing: however if the editor plugins calls repeatedly the outline command that might add up.

There seams to be some weird looping in the result, I will have a more in depth look.

voodoos avatar Aug 22 '22 13:08 voodoos

I was able to make a minimal example:

module Make () = struct
  module A = struct end
  module B = C.C1
end

Has the outline:

{
  "class": "return",
  "value": [
    {
      "name": "Make",
      "kind": "Module",
      "type": null,
      "children": [
        {
          "name": "B",
          "kind": "Module",
          "type": null,
          "children": [
              "name": "A",
              "kind": "Module",
              "type": null,
              "children": [],
            }
          ],
        },
        {
          "name": "A",
          "kind": "Module",
          "type": null,
        }
      ],
    }
  ],
}

Which is obviously wrong since A is not a child of B.

However if we give the definition of C (and thus if typing succeeds):

module C = struct
  module C1 = struct end
end

module Make () = struct
  module A = struct end
  module B = C.C1
end

Then we get the correct outline:

{
  "class": "return",
  "value": [
      "name": "Make",
      "kind": "Module",
      "type": null,
      "children": [
        {
          "name": "B",
          "kind": "Module",
          "type": null,
          "children": [],
          "deprecated": false
        },
        {
          "name": "A",
          "kind": "Module",
          "type": null,
          "children": [],
        }
      ],
    },
    {
      "name": "C",
      "kind": "Module",
      "type": null,
      "children": [
          "name": "C1",
          "kind": "Module",
          "type": null,
          "children": [],
          "deprecated": false
        }
      ],
    }
  ],
}

So incorrect nesting appear probably due to an issue with typing recovery. It is probably the cause of the slowdown in the vf_mir_translator.ml file. Since the project has no configuration (.merlin of dune) Merlin won't be able to type it since it doesn't know where to find the cmis and the incorrect typing recovery triggers the bug.

voodoos avatar Aug 22 '22 14:08 voodoos

The fix has been merge on Merlin master.

voodoos avatar Aug 24 '22 10:08 voodoos

Sorry I could not check here for a while. @rgrinberg the project is old and its build system is Makefile based. Even a single file with the mentioned code and without any project file or built binaries was triggering the bug for me. Fortunately, voodoos has already handled everything.

Nima-Rahimi-Foroushaani avatar Aug 29 '22 16:08 Nima-Rahimi-Foroushaani

Updated merlin. Should be fixed in the next release.

rgrinberg avatar Sep 07 '22 01:09 rgrinberg