Ticket #5 (closed defect: fixed)

Opened 6 years ago

Last modified 4 years ago

Physics Related Slowness

Reported by: mike Owned by: mike
Priority: normal Milestone: alpha-test
Component: server Version: 0.2
Keywords: Cc:
Estimated Effort: 1 day Platform: All
State: Conceptualizing Relative Size:

Description

Problem

Server runs slow with lots of objects.

Details

It seems that the problem is not as much with ODE as it is with running through all the objects in the area and calling Iterate on them. The loop plus calling _Set* for each object is a big time suck.

Profile Results

---------------
With IFs in object iters commented
---
UpdateClients-AddItem  1  0.000  0.000  0.000
Server.Iterate-Conman  300  0.000  0.000  0.097
Contain-UpdateClients  52  0.001  0.001  0.050
UpdateClients-SetVisualProperty  52  0.000  0.000  0.015
UpdateClients-SetPhysicsProperty  1  0.000  0.000  0.000
odeArea.IterateContents  300  0.117  0.150  35.192
odeArea.Collide  300  0.002  0.003  0.676
Server.Iterate  300  0.124  0.157  37.116
UpdateClients-SetPosition  8482  0.000  0.000  1.383
odeRealm.Iterate  300  0.001  0.001  0.329
UpdateClients-AddRange  1  0.000  0.000  0.000
UpdateClients-SetAngularVelocity  15601  0.000  0.000  4.321
odeArea.Iterate  300  0.121  0.153  36.205
Contain-AddContainedBy  52  0.000  0.000  0.020
UpdateClients-Prune  1  0.000  0.000  0.000
UpdateClients-AddMasterServer  2  0.000  0.000  0.001
UpdateClients-SetLinearVelocity  15600  0.000  0.000  4.326
UpdateClients-SetParentID  2  0.000  0.000  0.001
UpdateClients-AddSimulationServer  1  0.000  0.000  0.000
UpdateClients-SetName  2  0.000  0.000  0.001
UpdateClients-SetRotation  8482  0.000  0.000  2.378
300 iters in 46.46 seconds or 6.456510 ips
---------------
With object iters doing nothing
---
Contain-add dict  52  0.000  0.000  0.013
UpdateClients-SetID  1  0.000  0.000  0.000
UpdateClients-AddItem  1  0.000  0.000  0.000
Server.Iterate-Conman  300  0.000  0.000  0.094
Contain-UpdateClients  52  0.001  0.001  0.050
UpdateClients-SetVisualProperty  52  0.000  0.000  0.014
UpdateClients-SetPhysicsProperty  1  0.000  0.000  0.000
odeArea.IterateContents  300  0.000  0.000  0.098
odeArea.Collide  300  0.002  0.003  0.664
Server.Iterate  300  0.007  0.008  2.138
UpdateClients-SetPosition  52  0.000  0.000  0.014
odeRealm.Iterate  300  0.002  0.002  0.477
UpdateClients-AddRange  1  0.000  0.000  0.000
UpdateClients-SetAngularVelocity  1  0.000  0.000  0.000
odeArea.Iterate  300  0.004  0.004  1.092
Contain-AddContainedBy  52  0.000  0.000  0.020
UpdateClients-Prune  1  0.000  0.000  0.000
UpdateClients-AddMasterServer  2  0.000  0.000  0.001
UpdateClients-SetParentID  2  0.000  0.000  0.001
UpdateClients-AddSimulationServer  1  0.000  0.000  0.000
UpdateClients-SetName  2  0.000  0.000  0.001
UpdateClients-SetRotation  52  0.000  0.000  0.014
300 iters in 14.96 seconds or 20.049481 ips
------------
With object iters running ifs
---
Contain-add dict  52  0.000  0.000  0.013
UpdateClients-SetID  1  0.000  0.000  0.000
UpdateClients-AddItem  1  0.000  0.000  0.000
Server.Iterate-Conman  300  0.000  0.000  0.096
Contain-UpdateClients  52  0.001  0.001  0.049
UpdateClients-SetVisualProperty  52  0.000  0.000  0.014
UpdateClients-SetPhysicsProperty  1  0.000  0.000  0.000
odeArea.IterateContents  300  0.001  0.001  0.263
odeArea.Collide  300  0.002  0.003  0.663
Server.Iterate  300  0.008  0.009  2.315
UpdateClients-SetPosition  52  0.000  0.000  0.014
odeRealm.Iterate  300  0.002  0.002  0.495
UpdateClients-AddRange  1  0.000  0.000  0.000
UpdateClients-SetAngularVelocity  1  0.000  0.000  0.000
odeArea.Iterate  300  0.004  0.005  1.254
Contain-AddContainedBy  52  0.000  0.000  0.019
UpdateClients-Prune  1  0.000  0.000  0.000
UpdateClients-AddMasterServer  2  0.000  0.000  0.001
UpdateClients-SetParentID  2  0.000  0.000  0.001
UpdateClients-AddSimulationServer  1  0.000  0.000  0.000
UpdateClients-SetName  2  0.000  0.000  0.001
UpdateClients-SetRotation  52  0.000  0.000  0.014
300 iters in 14.96 seconds or 20.048059 ips
--------------
With profile in updateclients off
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.005  0.006  1.433
Contain-UpdateClients  52  0.000  0.000  0.015
odeArea.Iterate  300  0.008  0.010  2.445
Contain-AddContainedBy  52  0.000  0.000  0.020
odeArea.Collide  300  0.002  0.003  0.673
Server.Iterate  300  0.012  0.014  3.519
Contain-add dict  52  0.000  0.000  0.014
odeRealm.Iterate  300  0.002  0.002  0.487
Server.Iterate-Conman  300  0.000  0.000  0.099
300 iters in 14.97 seconds or 20.040902 ips
-----------------
Profile off and 100 objects
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.009  0.011  2.718
Contain-UpdateClients  102  0.000  0.000  0.029
odeArea.Iterate  300  0.015  0.018  4.351
Contain-AddContainedBy  102  0.000  0.000  0.039
odeArea.Collide  300  0.004  0.005  1.283
Server.Iterate  300  0.019  0.024  5.841
Contain-add dict  102  0.000  0.000  0.027
odeRealm.Iterate  300  0.003  0.004  0.891
Server.Iterate-Conman  300  0.000  0.000  0.101
300 iters in 14.98 seconds or 20.027859 ips
-----------------
Profile off and 500 objects
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.045  0.056  13.389
Contain-UpdateClients  502  0.000  0.000  0.145
odeArea.Iterate  300  0.075  0.091  22.626
Contain-AddContainedBy  502  0.000  0.000  0.190
odeArea.Collide  300  0.030  0.034  8.886
Server.Iterate  300  0.088  0.107  26.287
Contain-add dict  502  0.000  0.000  0.133
odeRealm.Iterate  300  0.010  0.014  3.055
Server.Iterate-Conman  300  0.000  0.000  0.102
300 iters in 34.06 seconds or 8.807123 ips
-----------------
Profile off and 500 objects and ifs gone
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.043  0.051  12.833
Contain-UpdateClients  502  0.000  0.000  0.143
odeArea.Iterate  300  0.074  0.115  22.248
Contain-AddContainedBy  502  0.000  0.000  0.190
odeArea.Collide  300  0.030  0.063  9.071
Server.Iterate  300  0.086  0.131  25.847
Contain-add dict  502  0.000  0.000  0.132
odeRealm.Iterate  300  0.010  0.013  3.007
Server.Iterate-Conman  300  0.000  0.000  0.100
300 iters in 31.19 seconds or 9.619341 ips
-----------------
With psycho (500 objs, ifs back)
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.035  0.045  10.624
Contain-UpdateClients  502  0.000  0.000  0.140
odeArea.Iterate  300  0.063  0.111  18.887
Contain-AddContainedBy  502  0.000  0.000  0.187
odeArea.Collide  300  0.026  0.065  7.928
Server.Iterate  300  0.073  0.125  21.971
Contain-add dict  502  0.000  0.000  0.128
odeRealm.Iterate  300  0.008  0.012  2.522
Server.Iterate-Conman  300  0.000  0.000  0.090
300 iters in 28.58 seconds or 10.496757 ips
----------------
Psyco, 500 objs, removed UpdateClients
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.019  0.019  5.669
Contain-UpdateClients  502  0.000  0.000  0.142
odeArea.Iterate  300  0.046  0.049  13.669
Contain-AddContainedBy  502  0.000  0.000  0.188
odeArea.Collide  300  0.026  0.029  7.658
Server.Iterate  300  0.056  0.063  16.788
Contain-add dict  502  0.000  0.000  0.131
odeRealm.Iterate  300  0.008  0.012  2.543
Server.Iterate-Conman  300  0.000  0.000  0.092
300 iters in 26.67 seconds or 11.249150 ips
----------------
Psyco, 500objs, Iterate object off
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.001  0.001  0.199
Contain-UpdateClients  502  0.000  0.000  0.142
odeArea.Iterate  300  0.025  0.029  7.481
Contain-AddContainedBy  502  0.000  0.000  0.187
odeArea.Collide  300  0.023  0.027  6.949
Server.Iterate  300  0.035  0.042  10.579
Contain-add dict  502  0.000  0.000  0.131
odeRealm.Iterate  300  0.008  0.012  2.540
Server.Iterate-Conman  300  0.000  0.000  0.089
300 iters in 15.30 seconds or 19.608626 ips
----------------
Psyco, 1000objs, Iterate object off (loop on)
---
 Name     Runs   Avg   Max   Total
odeArea.IterateContents  300  0.001  0.001  0.348
Contain-UpdateClients  1002  0.000  0.000  0.286
odeArea.Iterate  300  0.064  0.072  19.124
Contain-AddContainedBy  1002  0.000  0.000  0.370
odeArea.Collide  300  0.061  0.070  18.447
Server.Iterate  300  0.079  0.089  23.592
Contain-add dict  1002  0.000  0.000  0.262
odeRealm.Iterate  300  0.013  0.016  3.910
Server.Iterate-Conman  300  0.000  0.000  0.089
300 iters in 28.59 seconds or 10.491476 ips
-----------------
Psyco, 5000 objs, Iter loop off, autodisable, 499 objects to an area
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  3600  0.000  0.000  0.880
Contain-UpdateClients  5002  0.000  0.000  1.403
odeArea.Iterate  3600  0.007  0.002  23.850
Contain-AddContainedBy  5002  0.000  0.000  1.874
odeArea.Collide  3600  0.005  0.001  18.071
Server.Iterate  300  0.094  0.094  28.152
Contain-add dict  5002  0.000  0.000  1.293
odeRealm.Iterate  300  0.008  0.008  2.331
Server.Iterate-Conman  300  0.000  0.000  0.089
300 iters in 30.30 seconds or 9.901145 ips
-----------------
Psyco, 5000 objs, Iter loop off, autodisable, 249 objects to an area
---
Name     Runs   Avg   Max   Total
odeArea.IterateContents  6600  0.000  0.000  1.588
Contain-UpdateClients  5002  0.000  0.000  1.398
odeArea.Iterate  6600  0.003  0.003  20.230
Contain-AddContainedBy  5002  0.000  0.000  1.854
odeArea.Collide  6600  0.002  0.002  11.539
Server.Iterate  300  0.086  0.086  25.838
Contain-add dict  5002  0.000  0.000  0.285
odeRealm.Iterate  300  0.008  0.008  2.370
Server.Iterate-Conman  300  0.000  0.000  0.088
300 iters in 29.99 seconds or 10.002588 ips

Solution

First off, in the object's iterate function, check if it is disabled and if so, do nothing except return a specific value. The calling function (Area.Iterate) will check for this value and add the object to a list of inactive objects. The inactive objects will be Iterated less often. If they are active when iterated, then they are removed from the list. The server should keep a list of active objects per area so that it can use that list to call Iterate on. It would be nice to say only check a certain number of inactive objects per frame. That way, if there are lots of inactive objects in an area, it won't slow down.

This solution will stop working when there are lots of active objects in an area. In these cases, the server may slow down unfortunately. 100 active objects in an area doesn't seem to cause a problem, though. If the game were popular, all simulation servers would have high speed dual core dual processors (though this would mean we would have to rewrite some code to run areas in different threads to take advantage of SMP-- or just run 1 server instance per processor).

Change History

Changed 6 years ago by mike

  • version changed from pre-alpha to 0.2

Changed 6 years ago by mike

  • status changed from new to closed
  • platform set to All
  • state set to Conceptualizing
  • effort_estimate set to 1 day
  • resolution set to fixed

Solution

Created enabled and disabled spaces per area. This makes collision detection much much faster assuming you don't have a million enabled objects running around.

As part of a later enhancement, multiple enabled/disabled spaces based on object position could be used.

Changed 4 years ago by mike

  • milestone changed from beta-test to MV3D-0.32

Milestone beta-test deleted

Changed 4 years ago by mike

  • milestone changed from MV3D-0.32 to alpha-test

Setting the milestone back

Note: See TracTickets for help on using tickets.