[asterisk-commits] mmichelson: branch 1.6.0 r187425 - in /branches/1.6.0: ./ res/res_musiconhold.c

SVN commits to the Asterisk project asterisk-commits at lists.digium.com
Thu Apr 9 12:37:54 CDT 2009


Author: mmichelson
Date: Thu Apr  9 12:37:50 2009
New Revision: 187425

URL: http://svn.digium.com/svn-view/asterisk?view=rev&rev=187425
Log:
Merged revisions 187421,187424 via svnmerge from 
https://origsvn.digium.com/svn/asterisk/trunk

........
  r187421 | mmichelson | 2009-04-09 12:30:39 -0500 (Thu, 09 Apr 2009) | 21 lines
  
  Fix a crash in res_musiconhold when using cached realtime moh.
  
  The moh_register function links an mohclass and then immediately
  unrefs the class since the container now has a reference. The problem
  with using realtime music on hold is that the class is allocated,
  registered, and started in one fell swoop. The refcounting logic 
  resulted in the count being off by one. The same problem did not
  happen when using a static config because the allocation and registration
  of an mohclass is a separate operation from starting moh. This also did
  not affect non-cached realtime moh because the classes are not registered
  at all.
  
  I also have modified res_musiconhold to use the _t_ variants of the ao2_
  functions so that more info can be gleaned when attempting to trace the
  refcounts. I found this to be incredibly helpful for debugging this issue
  and there's no good reason to remove it.
  
  (closes issue #14661)
  Reported by: sum
........
  r187424 | mmichelson | 2009-04-09 12:34:39 -0500 (Thu, 09 Apr 2009) | 3 lines
  
  Use safe macro practices even though they really aren't necessary.
........

Modified:
    branches/1.6.0/   (props changed)
    branches/1.6.0/res/res_musiconhold.c

Propchange: branches/1.6.0/
------------------------------------------------------------------------------
Binary property 'trunk-merged' - no diff available.

Modified: branches/1.6.0/res/res_musiconhold.c
URL: http://svn.digium.com/svn-view/asterisk/branches/1.6.0/res/res_musiconhold.c?view=diff&rev=187425&r1=187424&r2=187425
==============================================================================
--- branches/1.6.0/res/res_musiconhold.c (original)
+++ branches/1.6.0/res/res_musiconhold.c Thu Apr  9 12:37:50 2009
@@ -1082,7 +1082,7 @@
 /*!
  * \note This function owns the reference it gets to moh
  */
-static int moh_register(struct mohclass *moh, int reload)
+static int moh_register(struct mohclass *moh, int reload, int unref)
 {
 	struct mohclass *mohclass = NULL;
 
@@ -1119,7 +1119,9 @@
 
 	ao2_link(mohclasses, moh);
 
-	moh = mohclass_unref(moh);
+	if (unref) {
+		moh = mohclass_unref(moh);
+	}
 	
 	return 0;
 }
@@ -1246,7 +1248,13 @@
 						mohclass = state->class;
 					}
 				}
-				moh_register(mohclass, 0);
+				/* We don't want moh_register to unref the mohclass because we do it at the end of this function as well.
+				 * If we allowed moh_register to unref the mohclass,too, then the count would be off by one. The result would
+				 * be that the destructor would be called when the generator on the channel is deactivated. The container then
+				 * has a pointer to a freed mohclass, so any operations involving the mohclass container would result in reading
+				 * invalid memory.
+				 */
+				moh_register(mohclass, 0, 0);
 			} else {
 				/* We don't register RT moh class, so let's init it manualy */
 
@@ -1510,7 +1518,7 @@
 		}
 
 		/* Don't leak a class when it's already registered */
-		if (!moh_register(class, reload)) {
+		if (!moh_register(class, reload, 1)) {
 			numclasses++;
 		}
 	}




More information about the asterisk-commits mailing list