Monday, November 08, 2010 at 12:05 AM.


on monitorThreads () { //called from scheduler.monitor, runs once a minute
	<<9/9/99; 7:45:50 PM by DW
		<<This is the thread manager code. We watch the runThreads pref. It it's true, we make sure that all the enabled threads are running. If it's false, we make sure none of the threads are running.
		<<You can call monitorThreads from a script if you want an immediate action. We do this in the menu command that starts/stops threads (Main menu, Scheduler sub-menu) and in the shutdown script (it kills all the threads before Frontier shuts down).
		<<11/30/00; 12:33:32 AM by JES
			<<Properly ignore undefined thread addresses in user.scheduler.threads.
				<<If the thread is an address which dereferences to an entry in an undefined table, no threads would run. Now two different try blocks are used, one for entries in  user.scheduler.threads, and once for tables at addresses specified in user.scheduler.threads.
		<<08/02/01; 6:09:34 PM by JES
			<<Kill threads whose enabled flag has been set to false.
	local (adrtemptable);
	bundle { //make sure temp table exists
		local (adrtable = @system.temp.scheduler);
		if not defined (adrtable^) {
			new (tabletype, adrtable)};
		adrtemptable = @adrtable^.idThreads;
		if not defined (adrtemptable^) {
			new (tabletype, adrtemptable)}};
	on killOneThread (adrthread) {
		namethread = nameof (adrthread^);
		if defined (adrtemptable^.[namethread]) {
			local (id = adrtemptable^.[namethread]);
			if thread.exists (id) {
				thread.kill (id);
				while thread.exists (id) {}};
			delete (@adrtemptable^.[namethread])}};
	if user.scheduler.prefs.runThreads { //start threads that need starting
		local (i, ct = sizeof (user.scheduler.threads), adrthread, namethread);
		for i = 1 to ct {
			adrthread = @user.scheduler.threads [i];
			namethread = nameof (adrthread^);
			try { //11/30/00 JES: deal with undefined thread addresses
				local (nomad = adrthread);
				while typeof (nomad^) == addresstype {
					nomad = nomad^};
				if typeof (nomad^) == tableType {
					if defined (nomad^.enabled) {
						if nomad^.enabled {
							local (fllaunch = true);
							if defined (adrtemptable^.[namethread]) {
								if thread.exists (adrtemptable^.[namethread]) {
									fllaunch = false}};
							if fllaunch {
								local (adrscript = @nomad^.script);
								try { //11/30/00 JES: deal with undefined thread addresses
									while typeof (adrscript^) == addresstype {
										adrscript = adrscript^};
									adrtemptable^.[namethread]  = thread.evaluate (string (adrscript) + "()");
									flsave = true}}}
						else { //kill threads that have been disabled
							killOneThread (adrthread)}}}}}}
	else { //kill any scheduled threads that are running
		local (i, ct = sizeof (user.scheduler.threads), adrthread, namethread);
		for i = 1 to ct {
			adrthread = @user.scheduler.threads [i];
			killOneThread (adrthread)}}}
<<bundle //test code
	<<monitorThreads ()

This listing is for code that runs in the OPML Editor environment. I created these listings because I wanted the search engines to index it, so that when I want to look up something in my codebase I don't have to use the much slower search functionality in my object database. Dave Winer.