v2ray-plugin icon indicating copy to clipboard operation
v2ray-plugin copied to clipboard

v2ray-plugin在openwrt和merlin系统,占用内存非常高?

Open hihua opened this issue 5 years ago • 7 comments

29946 14497 root S 658m 131% 0% v2ray-plugin

hihua avatar Mar 04 '20 13:03 hihua

go不适合嵌入式,go程序自带了一套运行库,而不是像c程序那样调用公共系统库,所以内存占用和文件大小都比c程序大。

CrazyBoyFeng avatar Mar 07 '20 09:03 CrazyBoyFeng

这个跟运行时库没什么关系,v2ray-plugin的可执行文件一共10MB左右,去哪里释放出600多MB的运行时库。

我也遇到了和题主相似的情况,但我随后用Go编译了一个Hello World,发现连一个Hello World都用了600多MB的内存,所以这个大概率是Go语言本身的bug。我已经给他们提了一个bug report了,在这里:https://github.com/golang/go/issues/39174

除此之外,我还找到了一个临时的解决方案,就是用ulimit限制一下内存的使用。我把原版的v2ray-plugin下载到了/etc/shadowsocks-libev/v2ray-plugin_linux_mipsle_sf,然后创建了一个脚本/etc/shadowsocks-libev/v2ray-plugin,里面的内容是

#!/bin/sh
ulimit -v 32768 # Limit memory usage to at most 32MB
trap : SIGTERM SIGINT

/etc/shadowsocks-libev/v2ray-plugin_linux_mipsle_sf "$@" &
V2RAY_PID=$!

wait $V2RAY_PID
kill $V2RAY_PID
echo "Killed ${V2RAY_PID}!"

接下来只要在shadowsocks的设置里指定插件路径为/etc/shadowsocks-libev/v2ray-plugin,问题就解决了,现在我一个v2ray-plugin进程只使用15MB左右的内存。

Gh0u1L5 avatar May 20 '20 14:05 Gh0u1L5

600MB只是虚拟内存的映射而已(TCMalloc也会有类似问题),具体数值要看RES

p.s. 我用龙芯(mips64le)跑那个用例程序,实际只占用869KB内存。

PID USER      PR  NI    VIRT    RES    SHR S  %CPU %MEM     TIME+ COMMAND 
21825 root      20   0  662912    896    768 R 106.2  0.0   2:37.91 ff      

mengzhuo avatar May 22 '20 03:05 mengzhuo

@mengzhuo 对,我跟Go那边的人聊过之后他们提醒了我600多只是虚拟内存了,但问题在于我在OpenWRT上跑v2ray-plugin真的会被OOM-killer反复杀进程,半分钟左右杀一次,网页时常出现Early EOF,用ulimit限制了虚拟内存大小之后才变得能够稳定运行。另外Go那边的人也反馈说mipsle似乎不应该分配600MB的虚拟内存,他们现在还在分析问题。

Gh0u1L5 avatar May 22 '20 03:05 Gh0u1L5

话说869KB的内存是没算.text section吗?我编译出来的一个Hello World就有2M大啊?

Gh0u1L5 avatar May 22 '20 03:05 Gh0u1L5

man top里有解释 我理解Go其实大头就是1象限,text section 没有你想像的多,binary 2MB里有不少是dwarf信息(gdb debug用的)

                              Private | Shared
                          1           |          2
     Anonymous  . stack               |
                . malloc()            |
                . brk()/sbrk()        | . POSIX shm*
                . mmap(PRIVATE, ANON) | . mmap(SHARED, ANON)
               -----------------------+----------------------
                . mmap(PRIVATE, fd)   | . mmap(SHARED, fd)
   File-backed  . pgms/shared libs    |
                          3           |          4

 RES  - anything occupying physical memory which, beginning with
        Linux-4.5, is the sum of the following three fields:
        RSan - quadrant 1 pages, which include any
               former quadrant 3 pages if modified
        RSfd - quadrant 3 and quadrant 4 pages
        RSsh - quadrant 2 pages

mengzhuo avatar May 22 '20 03:05 mengzhuo

这个跟运行时库没什么关系,v2ray-plugin的可执行文件一共10MB左右,去哪里释放出600多MB的运行时库。

我也遇到了和题主相似的情况,但我随后用Go编译了一个Hello World,发现连一个Hello World都用了600多MB的内存,所以这个大概率是Go语言本身的bug。我已经给他们提了一个bug report了,在这里:golang/go#39174

除此之外,我还找到了一个临时的解决方案,就是用ulimit限制一下内存的使用。我把原版的v2ray-plugin下载到了/etc/shadowsocks-libev/v2ray-plugin_linux_mipsle_sf,然后创建了一个脚本/etc/shadowsocks-libev/v2ray-plugin,里面的内容是

#!/bin/sh
ulimit -v 32768 # Limit memory usage to at most 32MB
trap : SIGTERM SIGINT

/etc/shadowsocks-libev/v2ray-plugin_linux_mipsle_sf "$@" &
V2RAY_PID=$!

wait $V2RAY_PID
kill $V2RAY_PID
echo "Killed ${V2RAY_PID}!"

接下来只要在shadowsocks的设置里指定插件路径为/etc/shadowsocks-libev/v2ray-plugin,问题就解决了,现在我一个v2ray-plugin进程只使用15MB左右的内存。

这个脚本,我在openwrt 19.07里试了一下,不行啊。 我目前的内存占用是291%,运行一会就挂掉了

Cuile avatar Jul 30 '21 02:07 Cuile