Assertion Failed and Pass Hash

Problems building or running the engine, queries about how to use features etc.
claustre
Goblin
Posts: 278
Joined: Thu Mar 23, 2006 10:35 am
Location: Toulouse, France

Assertion Failed and Pass Hash

Post by claustre »

Hello, like other people (http://www.ogre3d.org/phpBB2/viewtopic. ... air+second) my application sometimes raise this assertion :

Code: Select all

Assertion failed! 
 File: d:\ogredev\dagon\ogremain\src\og...rtinggrouping.cpp 
 Line: 341 
 
 Expression: retPair.second && "Error inserting new pass entry into PassGroupRenderableMap"
I was waiting for the new release (1.2.4) as it said that dirty pass hashes immediately on change rather than on load could solve my problem. However, I tested it this morning with no success :-(

Following this idea : http://www.ogre3d.org/phpBB2/viewtopic. ... air+second, every time a material modification occurs, I force a compilation and a reload, but this actually does not solve the problem for me.

I have two scene managers at the present time but this could be more in the future. Maybe it is also related to the special setup of my application ? Any idea will be helpfull...
User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19269
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66

Post by sinbad »

Damn, 1.2.4 definitely fixed the problem in the other thread, you must have a slightly different issue.

Basically what causes this is if the pass hash has been changed but there are still entries with the old hash in the renderqueue map. The reason this occurred before was because the dirtying was happening too late, perhaps in your case the dirtying is happening, but for some reason the Pass::processPendingPassUpdates call isn't sorting it out for you. This normally happens on RenderQueue::clear, therefore I think to have this problem you must have the following sequence:

1) clear render queue
2) add pass to renderqueue with old setup
3) change pass
4) add pass to render queue with new setup

It is not valid to change the pass during the process of rendering (any time during SceneManager::_renderScene), since the pass must be static for it to be properly queued for many objects.

Can you check your code for that kind of behaviour?
claustre
Goblin
Posts: 278
Joined: Thu Mar 23, 2006 10:35 am
Location: Toulouse, France

Post by claustre »

Ok thanks for these tips, I will look for this kind of behaviour in my code.

Just to be more efficient can you precise which changes on a pass could affect the hash value ? According to Ogre's source code it seems to be pass index and first and second texture unit state names, am I right ? This will speed up my checks...
User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19269
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66

Post by sinbad »

Yep, pass index and first 2 textures in Dagon (more configurable in Eihort).
claustre
Goblin
Posts: 278
Joined: Thu Mar 23, 2006 10:35 am
Location: Toulouse, France

Post by claustre »

Just a couple of questions :

I was wondering about multiple scene managers issues...
No possible problem if I have multiple copies of the same material used in both scene managers ?

What about the hash code if similar pass number and texture settings for different materials ?
User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19269
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66

Post by sinbad »

No problem on both counts. In the extremely rare case that you do get a hash collision then both will get rendered together - not strictly correct in terms of optimisation but this should be rare enough not to matter.

The only way you can get this assert is if the hash of a pass has changed whilst instances of it are already in the map.
User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19269
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66

Post by sinbad »

Hmm, actually multiple scene managers could cause a problem here.

It's during RenderQueue::clear() that dirty hashes are removed from the queue, so that when they are put back, it will be with the updated hash. However, because this is called from SceneManager::_renderScene, the whole sequence of checking and then clearing the dirty list is done within one SceneManager, so when the render queue is cleared for the other one the passes are no longer marked as dirty.

What is needed is the sequence:

- SM1 clear render queue
- SM2 clear render queue
- Process pending pass updates
- render..

However this is rather difficult to engineer generically given how the SceneManager might be invoked. We'd have to move the process of clearing the queues and processing the updates outside of the SceneManager itself, perhaps into Root somewhere. Hmm.
claustre
Goblin
Posts: 278
Joined: Thu Mar 23, 2006 10:35 am
Location: Toulouse, France

Post by claustre »

Yes you are right I think that is the point.

Well, I am not still familiar with the underlying process of pending pass updates but actually the problem is maybe more simple. As we can work with multiple scene managers and not singleton, it is strange to use static members such as Pass::clearDirtyHashList() or Pass::processPendingPassUpdates(). Maybe all of this should be scene-based and not global... But maybe I am wrong as I am just discovering the "thing" and trying to understand...
User avatar
DimA
Halfling
Posts: 59
Joined: Tue Jan 10, 2006 12:52 pm
Location: Ukraine
x 6

Post by DimA »

Hi All!

I've got the same problem for multi-scenes!
Indeed I have a material editor in my program and several scene managers. Then I change a material on the fly it causes the same assertion.

I've wrote the special method to avoid the situation:

Code: Select all

void CGlobals::updateSceneManagersAfterMaterialsChange()
{
	if(m_Root && (Ogre::Pass::getDirtyHashList().size()!=0 || Ogre::Pass::getPassGraveyard().size()!=0))
	{
		Ogre::SceneManagerEnumerator::SceneManagerIterator scenesIter = m_Root->getSceneManagerIterator();
		
		while(scenesIter.hasMoreElements())
		{
			 Ogre::SceneManager* pScene = scenesIter.getNext();
			 if(pScene)
			 {
				Ogre::RenderQueue* pQueue = pScene->getRenderQueue();
				if(pQueue)
				{
					Ogre::RenderQueue::QueueGroupIterator groupIter = pQueue->_getQueueGroupIterator();
					while(groupIter.hasMoreElements())
					{
						Ogre::RenderQueueGroup* pGroup = groupIter.getNext();
						if(pGroup)
							pGroup->clear(false);
					}//end_while(groupIter.hasMoreElements())
				}//end_if(pScene)
			 }//end_if(pScene)
		}//end_while(scenesIter.hasMoreElements())		
		
		// Now trigger the pending pass updates
        Ogre::Pass::processPendingPassUpdates();

	}//end_if(m_Root..
}
So, I do call this method after the materials changing.

Hope this solution can be helpful.
noisy
Halfling
Posts: 55
Joined: Tue May 29, 2007 10:04 am
Location: Karlsruhe, Germany

Post by noisy »

thank you :D
seems to fix the problem
pra
Halfling
Posts: 55
Joined: Sat Jul 15, 2006 4:03 pm

Post by pra »

just encountered this assertation failure. i have 2 scene managers, one for the level and one just to display a compass needle (via Render to texture and cegui).
It occurs as soon as I use an animated material, like this one:

Code: Select all

material test/sparkreal
{
	technique
	{
		pass
		{
			alpha_rejection greater 150
			scene_blend alpha_blend
		    cull_hardware none
            cull_software none
			texture_unit
			{
				anim_texture spark1.png spark2.png spark3.png 0.5 
			}
		}
	}
}
i can see it animate briefly when the object is created, and then the error occurs.

DimA's function does not help, but i do not create dynamic materials, just call entity->setMaterialName().

edit: using OGRE 1.4.7 [Eihort], SDK.
and clicking "retry to debug the application" is pretty much useless, since it stops at mRoot->startrendering()

edit2: the exact error:
Image

edit3: i'm creating the rendertexture like this:

Code: Select all

compSceneMgr= mRoot->createSceneManager(ST_GENERIC);
	compNeedleNode = compSceneMgr->getRootSceneNode()->createChildSceneNode();
	Entity *ent = compSceneMgr->createEntity("compassent","CompassNeedle.mesh");

	SceneNode *meshNode = compNeedleNode->createChildSceneNode();
	meshNode->attachObject(ent);

	compassCam = compSceneMgr->createCamera("compasscam");
	compassWnd = wmgr->getWindow("compass");
	unsigned int width = compassWnd->getPixelSize().d_width;
	unsigned int height = compassWnd->getPixelSize().d_height;
	
	TexturePtr renderTex = TextureManager::getSingleton().createManual( "CompassRttTex", 
		ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME, TEX_TYPE_2D, 
		width, height, 0, PF_R8G8B8A8, TU_RENDERTARGET );

	
	
	compassCam->setAspectRatio(Real(width) / Real(height));
	compassCam->setPosition(0,1.2,0);
	
	compassCam->pitch(Degree(-90));
	compassCam->setNearClipDistance(0.01);
	
	RenderTarget *rttTex = renderTex->getBuffer()->getRenderTarget();
	Viewport *v = rttTex->addViewport(compassCam);
	v->setClearEveryFrame(true);
	v->setBackgroundColour(ColourValue(0,0,0,0));
	
    

    MaterialPtr mat = MaterialManager::getSingleton().create("CompassRttMat",
        ResourceGroupManager::DEFAULT_RESOURCE_GROUP_NAME);
	TextureUnitState* t = mat->getTechnique(0)->getPass(0)->createTextureUnitState("CompassRttTex");
    
  
	t->setTextureAddressingMode(TextureUnitState::TAM_CLAMP);
	
	CEGUI::Texture* ceguiTex = mGUIRenderer->createTexture(renderTex);

	CEGUI::String imageSetName = "compassimgset";
	Imageset* textureImageSet = ImagesetManager::getSingleton().createImageset(imageSetName, ceguiTex);

	textureImageSet->defineImage("compassneedle", Point(0.0f, 0.0f), Size(ceguiTex->getWidth(), ceguiTex->getHeight()), Point(0.0f,0.0f));
	

	compassWnd->setProperty("Image", "set:"+imageSetName+" image:compassneedle");
	
(copypaste from the sample)
pra
Halfling
Posts: 55
Joined: Sat Jul 15, 2006 4:03 pm

Post by pra »

ok, now things get weird. this error only occurs if the animated texture is defined as "anim_texture tex1.png tex2.png tex3.png 0.5". It works perfectly if I use "anim_texture tex.png 3 0.5"

that's fine for me since I have an easy workaround now, but this seems to be an ogre bug to me...
pra
Halfling
Posts: 55
Joined: Sat Jul 15, 2006 4:03 pm

Post by pra »

now it stopped working at all...
updated to 1.4.8, nothing changed.

If i create any entity with an animated material while using render to texture, it just crashes with the above mentioned error. It does not matter anymore how the material is defined...

edit: ok, just seen this:
http://www.ogre3d.org/mantis/view.php?id=130
well, does anyone know a workaround that could help me here? I'm afraid I don't really understand Ogre's inner workings good enough...
User avatar
sinbad
OGRE Retired Team Member
OGRE Retired Team Member
Posts: 19269
Joined: Sun Oct 06, 2002 11:19 pm
Location: Guernsey, Channel Islands
x 66

Post by sinbad »

Did you try DimA's approach? That's all we have to offer atm really, other than telling you not to dynamically change material structures when you have > 1 scene manager.
pra
Halfling
Posts: 55
Joined: Sat Jul 15, 2006 4:03 pm

Post by pra »

yes, but i'm not sure when I have to call this function. I called it after creating the rendertexture, that did not work. then tried in framestarted and/or frame ended, same result.
The thing is, I do not dynamically change materials...
.overlord.
Halfling
Posts: 52
Joined: Wed Jun 06, 2007 5:01 pm

Post by .overlord. »

i also have this issue with a particle that uses the anim_texture
where you explicitly say the images.

if i switch to the other way, just saying the base + # it works fine

weird

running HEAD, weirdly enough worked fine before the switch to
svn so something around then must have changed this behavior
.overlord.
Halfling
Posts: 52
Joined: Wed Jun 06, 2007 5:01 pm

Post by .overlord. »

.overlord. wrote:i also have this issue with a particle that uses the anim_texture
where you explicitly say the images.

if i switch to the other way, just saying the base + # it works fine

weird

running HEAD, weirdly enough worked fine before the switch to
svn so something around then must have changed this behavior
making this change did fix some of the issues i think but i
still have problems with ones with the base + # anim_texture.
it seems to be only related to materials that have animated textures.
johny5
Kobold
Posts: 38
Joined: Sat Mar 25, 2006 5:52 pm

Re: Assertion Failed and Pass Hash

Post by johny5 »

Ogre v1.6.0 and bug still exists.

To solve, I removed changing of anim_texture frame from the rendering stage to the update, and then used DimA approach. It helped.