BenChung / KRPC.jl

A kRPC client for Julia
MIT License
3 stars 4 forks source link

KRPC fails after repeated calls for `Name` across several modules and parts. #16

Closed Rhahi closed 1 week ago

Rhahi commented 1 year ago

Hello,

I have been working with engine cluster configurations, and then found out that KRPC gives up after numerous calls fetching module names. I was trying to cache some modules for re-use later, and to do that I needed to match their string name.

I don't know what's wrong here, other than not doing too many calls, so I need your help to fix the problem.

As usual, I start with importing common modules, and setting up vessels object.

Note that these tests are performed with Realism Overhaul, so I think in vanilla it will last a bit longer (due to less modules per parts)

import KRPC.Interface.SpaceCenter as SC
import KRPC.Interface.SpaceCenter.RemoteTypes as SCR
import KRPC.Interface.SpaceCenter.Helpers as SCH

... (get vessel object)
ves::SCR.Vessel = ...
parts = SCH.Parts(ves) |> SCH.All
part = parts[1]

The error appers when I query for Name call several times across several parts.

# breaks after number 82, or while processing the 4th part.
counter = 0
for p ∈ parts[1:10]
    modules = SCH.Modules(p)
    println("new part")
    for m ∈ modules
        counter += 1
        println(counter)
        SCH.Name(m)
    end
end

Interestingly, doing this on fewer parts does not cause any problem.

# works fine, even though I do this 5 times.
counter = 0
for i = 1:5
    for p ∈ parts[1:3]
        modules = SCH.Modules(p)
        println("new module")
        for m ∈ modules
            counter += 1
            println(counter)
            SCH.Name(m)
        end
    end
end

Note that in this case the script broke during the 4th part, but I don't think there is anything magical about number 4; during my cluster engine test I failed while parsing the 5th engine, (after naming 120-ish modules).

So I am assuming that there might be some kind of total number of "unique" object count or total amount of memory that KRPC.jl can track?

I almost forgot to show the stacktrace. Here are two examples.

# the error I get when running the above example, but with part 1:4. (or 1:10, they stop at the same place)

The KRPC server returned an error.
Service: 
Description:
===============
Non-static method requires a target.

Server internal stack trace:
===============

  at System.Reflection.MonoMethod.Invoke (System.Object obj, System.Reflection.BindingFlags invokeAttr, System.Reflection.Binder binder, System.Object[] parameters, System.Globalization.CultureInfo culture) [0x0004c] in <9577ac7a62ef43179789031239ba8798>:0 
  at System.Reflection.MethodBase.Invoke (System.Object obj, System.Object[] parameters) [0x00000] in <9577ac7a62ef43179789031239ba8798>:0 
  at KRPC.Service.ClassMethodHandler.Invoke (System.Object[] arguments) [0x00044] in :0 
  at KRPC.Service.Services.ExecuteCall (KRPC.Service.Scanner.ProcedureSignature procedure, System.Object[] arguments) [0x00036] in :0 

Stacktrace:
 [1] handle_potential_error(result::KRPC.krpc.schema.Response)
   @ KRPC ~/.julia/dev/KRPC/src/connection.jl:151
 [2] macro expansion
   @ ~/.julia/dev/KRPC/src/message.jl:45 [inlined]
 [3] kerbal(c::KRPC.KRPCConnection, calls::Tuple{KRPC.Interface.SpaceCenter.Module_get_Name})
   @ KRPC ~/.julia/dev/KRPC/src/message.jl:40
 [4] kerbal
   @ ~/.julia/dev/KRPC/src/message.jl:14 [inlined]
 [5] Name
   @ ~/.julia/dev/KRPC/src/generated.jl:13781 [inlined]
 [6] top-level scope
   @ ~/.julia/dev/SpaceLib/prototype/cluster.ipynb:9
# the error I got while testing live code
    "name": "KRPC.KRPCError",
    "message": "The KRPC server returned an error.
    Service: 
    Description:
    ===============
    Non-static method requires a target.

    Server internal stack trace:
    ===============

      at System.Reflection.MonoMethod.Invoke (System.Object obj, System.Reflection.BindingFlags invokeAttr, System.Reflection.Binder binder, System.Object[] parameters, System.Globalization.CultureInfo culture) [0x0004c] in <9577ac7a62ef43179789031239ba8798>:0 \r
      at System.Reflection.MethodBase.Invoke (System.Object obj, System.Object[] parameters) [0x00000] in <9577ac7a62ef43179789031239ba8798>:0 \r
      at KRPC.Service.ClassMethodHandler.Invoke (System.Object[] arguments) [0x00044] in <bfca7052818745ee95133536e4da4f10>:0 \r
      at KRPC.Service.Services.ExecuteCall (KRPC.Service.Scanner.ProcedureSignature procedure, System.Object[] arguments) [0x00036] in <bfca7052818745ee95133536e4da4f10>:0 
    ",
    "stack": "The KRPC server returned an error.
    Service: 
    Description:
    ===============
    Non-static method requires a target.

    Server internal stack trace:
    ===============

      at System.Reflection.MonoMethod.Invoke (System.Object obj, System.Reflection.BindingFlags invokeAttr, System.Reflection.Binder binder, System.Object[] parameters, System.Globalization.CultureInfo culture) [0x0004c] in <9577ac7a62ef43179789031239ba8798>:0 \r
      at System.Reflection.MethodBase.Invoke (System.Object obj, System.Object[] parameters) [0x00000] in <9577ac7a62ef43179789031239ba8798>:0 \r
      at KRPC.Service.ClassMethodHandler.Invoke (System.Object[] arguments) [0x00044] in <bfca7052818745ee95133536e4da4f10>:0 \r
      at KRPC.Service.Services.ExecuteCall (KRPC.Service.Scanner.ProcedureSignature procedure, System.Object[] arguments) [0x00036] in <bfca7052818745ee95133536e4da4f10>:0 

    Stacktrace:
     [1] handle_potential_error(result::KRPC.krpc.schema.Response)
       @ KRPC ~/.julia/dev/KRPC/src/connection.jl:151
     [2] macro expansion
       @ ~/.julia/dev/KRPC/src/message.jl:45 [inlined]
     [3] kerbal(c::KRPC.KRPCConnection, calls::Tuple{KRPC.Interface.SpaceCenter.Module_get_Name})
       @ KRPC ~/.julia/dev/KRPC/src/message.jl:40
     [4] kerbal
       @ ~/.julia/dev/KRPC/src/message.jl:14 [inlined]
     [5] Name
       @ ~/.julia/dev/KRPC/src/generated.jl:13781 [inlined]
     [6] getmodule(part::KRPC.Interface.SpaceCenter.RemoteTypes.Part, name::String, idx::Int64)
       @ SpaceLib.PartModule ~/.julia/dev/SpaceLib/src/partmodule/partmodule.jl:15
     [7] getmodule
       @ ~/.julia/dev/SpaceLib/src/partmodule/partmodule.jl:12 [inlined]
     [8] RealEngine(part::KRPC.Interface.SpaceCenter.RemoteTypes.Part)
       @ SpaceLib.Engine ~/.julia/dev/SpaceLib/src/partmodule/engine.jl:118
     [9] top-level scope
       @ ~/.julia/dev/SpaceLib/prototype/cluster.ipynb:2"

Updates

This is probably an integeroverflow issue.

parts = SCH.Parts(sp.ves)
part = SCH.WithTag(parts, "g3")[1]

for i = 1:128
    engine = SCH.Engine(part)
    println(engine.id)
    props = SCH.Propellants(engine)
end

calling engine (but doing some other calling in between) several times will cause a crash when the ID reaches 128!

Rhahi commented 1 year ago

This makes me think that the supposed "limitation on number of objects" might be the reason why I had to restart the KRPC every launch to not get those "mismatched" errors.

Rhahi commented 1 year ago

I was doubting whether if this is a bug in KRPC.jl or just kRPC in general, so I tested a similar code with the same spacecraft using the python client, so it is probably a KRPC.jl bug.

import krpc
conn = krpc.connect("Test", "10.0.0.51")
sc = conn.space_center
ves = sc.active_vessel
for p in ves.parts.all:
    for m in p.modules:
        print(m.name)

this code worked for me.

Rhahi commented 1 year ago

I found the fix. PR coming in soon.