diff options
Diffstat (limited to 'OpenSim/Region/Physics/OdePlugin/OdePlugin.cs')
-rw-r--r-- | OpenSim/Region/Physics/OdePlugin/OdePlugin.cs | 96 |
1 files changed, 70 insertions, 26 deletions
diff --git a/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs b/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs index 1c16cfb..66af095 100644 --- a/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs +++ b/OpenSim/Region/Physics/OdePlugin/OdePlugin.cs | |||
@@ -16,7 +16,7 @@ | |||
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY | 16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS'' AND ANY |
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | 17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | 18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | 19 | * DISCLAIMEd. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY |
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | 20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | 21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | 22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
@@ -46,10 +46,12 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
46 | { | 46 | { |
47 | private static readonly log4net.ILog m_log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); | 47 | private static readonly log4net.ILog m_log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); |
48 | 48 | ||
49 | private CollisionLocker ode; | ||
49 | private OdeScene _mScene; | 50 | private OdeScene _mScene; |
50 | 51 | ||
51 | public OdePlugin() | 52 | public OdePlugin() |
52 | { | 53 | { |
54 | ode = new CollisionLocker(); | ||
53 | } | 55 | } |
54 | 56 | ||
55 | public bool Init() | 57 | public bool Init() |
@@ -61,7 +63,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
61 | { | 63 | { |
62 | if (_mScene == null) | 64 | if (_mScene == null) |
63 | { | 65 | { |
64 | _mScene = new OdeScene(); | 66 | _mScene = new OdeScene(ode); |
65 | } | 67 | } |
66 | return (_mScene); | 68 | return (_mScene); |
67 | } | 69 | } |
@@ -74,7 +76,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
74 | public void Dispose() | 76 | public void Dispose() |
75 | { | 77 | { |
76 | 78 | ||
77 | d.CloseODE(); | 79 | |
78 | } | 80 | } |
79 | } | 81 | } |
80 | 82 | ||
@@ -82,6 +84,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
82 | { | 84 | { |
83 | private static readonly log4net.ILog m_log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); | 85 | private static readonly log4net.ILog m_log = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); |
84 | 86 | ||
87 | CollisionLocker ode; | ||
85 | // TODO: this should be hard-coded in some common place | 88 | // TODO: this should be hard-coded in some common place |
86 | private const uint m_regionWidth = 256; | 89 | private const uint m_regionWidth = 256; |
87 | private const uint m_regionHeight = 256; | 90 | private const uint m_regionHeight = 256; |
@@ -137,8 +140,9 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
137 | /// Sets many properties that ODE requires to be stable | 140 | /// Sets many properties that ODE requires to be stable |
138 | /// These settings need to be tweaked 'exactly' right or weird stuff happens. | 141 | /// These settings need to be tweaked 'exactly' right or weird stuff happens. |
139 | /// </summary> | 142 | /// </summary> |
140 | public OdeScene() | 143 | public OdeScene(CollisionLocker dode) |
141 | { | 144 | { |
145 | ode = dode; | ||
142 | nearCallback = near; | 146 | nearCallback = near; |
143 | triCallback = TriCallback; | 147 | triCallback = TriCallback; |
144 | triArrayCallback = TriArrayCallback; | 148 | triArrayCallback = TriArrayCallback; |
@@ -178,6 +182,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
178 | 182 | ||
179 | lock (OdeLock) | 183 | lock (OdeLock) |
180 | { | 184 | { |
185 | |||
181 | // Creat the world and the first space | 186 | // Creat the world and the first space |
182 | world = d.WorldCreate(); | 187 | world = d.WorldCreate(); |
183 | space = d.HashSpaceCreate(IntPtr.Zero); | 188 | space = d.HashSpaceCreate(IntPtr.Zero); |
@@ -268,8 +273,14 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
268 | // We'll be calling near recursivly if one | 273 | // We'll be calling near recursivly if one |
269 | // of them is a space to find all of the | 274 | // of them is a space to find all of the |
270 | // contact points in the space | 275 | // contact points in the space |
271 | 276 | try | |
272 | d.SpaceCollide2(g1, g2, IntPtr.Zero, nearCallback); | 277 | { |
278 | d.SpaceCollide2(g1, g2, IntPtr.Zero, nearCallback); | ||
279 | } | ||
280 | catch (System.AccessViolationException) | ||
281 | { | ||
282 | m_log.Warn("[PHYSICS]: Unable to collide test a space"); | ||
283 | } | ||
273 | //Colliding a space or a geom with a space or a geom. so drill down | 284 | //Colliding a space or a geom with a space or a geom. so drill down |
274 | 285 | ||
275 | //Collide all geoms in each space.. | 286 | //Collide all geoms in each space.. |
@@ -304,7 +315,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
304 | name2 = "null"; | 315 | name2 = "null"; |
305 | } | 316 | } |
306 | 317 | ||
307 | //if (id == d.GeomClassID.TriMeshClass) | 318 | //if (id == d.GeomClassId.TriMeshClass) |
308 | //{ | 319 | //{ |
309 | // m_log.Info("near: A collision was detected between {1} and {2}", 0, name1, name2); | 320 | // m_log.Info("near: A collision was detected between {1} and {2}", 0, name1, name2); |
310 | //System.Console.WriteLine("near: A collision was detected between {1} and {2}", 0, name1, name2); | 321 | //System.Console.WriteLine("near: A collision was detected between {1} and {2}", 0, name1, name2); |
@@ -321,6 +332,10 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
321 | m_log.Error("[PHYSICS]: The Operating system shut down ODE because of corrupt memory. This could be a result of really irregular terrain. If this repeats continuously, restart using Basic Physics and terrain fill your terrain. Restarting the sim."); | 332 | m_log.Error("[PHYSICS]: The Operating system shut down ODE because of corrupt memory. This could be a result of really irregular terrain. If this repeats continuously, restart using Basic Physics and terrain fill your terrain. Restarting the sim."); |
322 | base.TriggerPhysicsBasedRestart(); | 333 | base.TriggerPhysicsBasedRestart(); |
323 | } | 334 | } |
335 | catch (System.AccessViolationException) | ||
336 | { | ||
337 | m_log.Warn("[PHYSICS]: Unable to collide test an object"); | ||
338 | } | ||
324 | 339 | ||
325 | PhysicsActor p1; | 340 | PhysicsActor p1; |
326 | PhysicsActor p2; | 341 | PhysicsActor p2; |
@@ -438,7 +453,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
438 | 453 | ||
439 | if (contacts[i].depth >= 0.25f) | 454 | if (contacts[i].depth >= 0.25f) |
440 | { | 455 | { |
441 | // Don't collide, one or both prim will explode. | 456 | // Don't collide, one or both prim will expld. |
442 | 457 | ||
443 | 458 | ||
444 | op1.m_interpenetrationcount++; | 459 | op1.m_interpenetrationcount++; |
@@ -596,8 +611,14 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
596 | // And we'll run this again against the avatar and the space segment | 611 | // And we'll run this again against the avatar and the space segment |
597 | // This will return with a bunch of possible objects in the space segment | 612 | // This will return with a bunch of possible objects in the space segment |
598 | // and we'll run it again on all of them. | 613 | // and we'll run it again on all of them. |
599 | 614 | try | |
600 | d.SpaceCollide2(space, chr.Shell, IntPtr.Zero, nearCallback); | 615 | { |
616 | d.SpaceCollide2(space, chr.Shell, IntPtr.Zero, nearCallback); | ||
617 | } | ||
618 | catch (AccessViolationException) | ||
619 | { | ||
620 | m_log.Warn("[PHYSICS]: Unable to space collide"); | ||
621 | } | ||
601 | //float terrainheight = GetTerrainHeightAtXY(chr.Position.X, chr.Position.Y); | 622 | //float terrainheight = GetTerrainHeightAtXY(chr.Position.X, chr.Position.Y); |
602 | //if (chr.Position.Z + (chr.Velocity.Z * timeStep) < terrainheight + 10) | 623 | //if (chr.Position.Z + (chr.Velocity.Z * timeStep) < terrainheight + 10) |
603 | //{ | 624 | //{ |
@@ -616,8 +637,14 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
616 | // This if may not need to be there.. it might be skipped anyway. | 637 | // This if may not need to be there.. it might be skipped anyway. |
617 | if (d.BodyIsEnabled(chr.Body) && (!chr.m_disabled)) | 638 | if (d.BodyIsEnabled(chr.Body) && (!chr.m_disabled)) |
618 | { | 639 | { |
619 | 640 | try | |
620 | d.SpaceCollide2(space, chr.prim_geom, IntPtr.Zero, nearCallback); | 641 | { |
642 | d.SpaceCollide2(space, chr.prim_geom, IntPtr.Zero, nearCallback); | ||
643 | } | ||
644 | catch (AccessViolationException) | ||
645 | { | ||
646 | m_log.Warn("[PHYSICS]: Unable to space collide"); | ||
647 | } | ||
621 | //calculateSpaceForGeom(chr.Position) | 648 | //calculateSpaceForGeom(chr.Position) |
622 | //foreach (OdePrim ch2 in _prims) | 649 | //foreach (OdePrim ch2 in _prims) |
623 | /// should be a separate space -- lots of avatars will be N**2 slow | 650 | /// should be a separate space -- lots of avatars will be N**2 slow |
@@ -634,7 +661,14 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
634 | //} | 661 | //} |
635 | //} | 662 | //} |
636 | } | 663 | } |
637 | d.SpaceCollide2(LandGeom, chr.prim_geom, IntPtr.Zero, nearCallback); | 664 | try |
665 | { | ||
666 | d.SpaceCollide2(LandGeom, chr.prim_geom, IntPtr.Zero, nearCallback); | ||
667 | } | ||
668 | catch (AccessViolationException) | ||
669 | { | ||
670 | m_log.Warn("[PHYSICS]: Unable to space collide"); | ||
671 | } | ||
638 | } | 672 | } |
639 | } | 673 | } |
640 | else | 674 | else |
@@ -663,7 +697,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
663 | pos.X = position.X; | 697 | pos.X = position.X; |
664 | pos.Y = position.Y; | 698 | pos.Y = position.Y; |
665 | pos.Z = position.Z; | 699 | pos.Z = position.Z; |
666 | OdeCharacter newAv = new OdeCharacter(avName, this, pos); | 700 | OdeCharacter newAv = new OdeCharacter(avName, this, pos, ode); |
667 | _characters.Add(newAv); | 701 | _characters.Add(newAv); |
668 | return newAv; | 702 | return newAv; |
669 | } | 703 | } |
@@ -1007,7 +1041,7 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
1007 | OdePrim newPrim; | 1041 | OdePrim newPrim; |
1008 | lock (OdeLock) | 1042 | lock (OdeLock) |
1009 | { | 1043 | { |
1010 | newPrim = new OdePrim(name, this, targetspace, pos, siz, rot, mesh, pbs, isphysical); | 1044 | newPrim = new OdePrim(name, this, targetspace, pos, siz, rot, mesh, pbs, isphysical, ode); |
1011 | 1045 | ||
1012 | _prims.Add(newPrim); | 1046 | _prims.Add(newPrim); |
1013 | } | 1047 | } |
@@ -1203,8 +1237,15 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
1203 | actor.Move(timeStep); | 1237 | actor.Move(timeStep); |
1204 | actor.collidelock = true; | 1238 | actor.collidelock = true; |
1205 | } | 1239 | } |
1240 | |||
1241 | ode.dlock(world); | ||
1206 | 1242 | ||
1207 | collision_optimized(timeStep); | 1243 | collision_optimized(timeStep); |
1244 | |||
1245 | |||
1246 | |||
1247 | ode.dunlock(world); | ||
1248 | |||
1208 | try | 1249 | try |
1209 | { | 1250 | { |
1210 | d.WorldQuickStep(world, ODE_STEPSIZE); | 1251 | d.WorldQuickStep(world, ODE_STEPSIZE); |
@@ -1228,25 +1269,28 @@ namespace OpenSim.Region.Physics.OdePlugin | |||
1228 | actor.UpdatePositionAndVelocity(); | 1269 | actor.UpdatePositionAndVelocity(); |
1229 | } | 1270 | } |
1230 | 1271 | ||
1231 | bool processedtaints = false; | 1272 | if (!ode.lockquery()) |
1232 | foreach (OdePrim prim in _taintedPrim) | ||
1233 | { | 1273 | { |
1234 | prim.ProcessTaints(timeStep); | 1274 | bool processedtaints = false; |
1235 | if (prim.m_taintremove) | 1275 | foreach (OdePrim prim in _taintedPrim) |
1236 | { | 1276 | { |
1237 | RemovePrimThreadLocked(prim); | 1277 | prim.ProcessTaints(timeStep); |
1238 | } | 1278 | if (prim.m_taintremove) |
1239 | processedtaints = true; | 1279 | { |
1240 | prim.m_collisionscore = 0; | 1280 | RemovePrimThreadLocked(prim); |
1281 | } | ||
1282 | processedtaints = true; | ||
1283 | prim.m_collisionscore = 0; | ||
1284 | } | ||
1285 | if (processedtaints) | ||
1286 | _taintedPrim = new List<OdePrim>(); | ||
1241 | } | 1287 | } |
1242 | |||
1243 | foreach (OdePrim prim in _activeprims) | 1288 | foreach (OdePrim prim in _activeprims) |
1244 | { | 1289 | { |
1245 | prim.m_collisionscore = 0; | 1290 | prim.m_collisionscore = 0; |
1246 | } | 1291 | } |
1247 | 1292 | ||
1248 | if (processedtaints) | 1293 | |
1249 | _taintedPrim = new List<OdePrim>(); | ||
1250 | 1294 | ||
1251 | if (timeStep < 0.2f) | 1295 | if (timeStep < 0.2f) |
1252 | { | 1296 | { |