function execOnLoad(mm) {
  // When module is unloaded, execOnLoad is async.
  let execCalled1 = false;
  mm.execOnLoad('a', () => {
    execCalled1 = true;
  });
  assertFalse('module "a" should not be loaded', mm.isModuleLoaded('a'));
  assertTrue('module "a" should be loading', mm.isModuleLoading('a'));
  assertFalse('execCalled1 should not be set yet', execCalled1);
  assertTrue('ModuleManager should be active', mm.isActive());
  assertFalse('ModuleManager should not be user active', mm.isUserActive());
  clock.tick(5);
  assertTrue('module "a" should be loaded', mm.isModuleLoaded('a'));
  assertFalse('module "a" should not be loading', mm.isModuleLoading('a'));
  assertTrue('execCalled1 should be set', execCalled1);
  assertFalse('ModuleManager should not be active', mm.isActive());
  assertFalse('ModuleManager should not be user active', mm.isUserActive());

  // When module is already loaded, execOnLoad is still async unless
  // specified otherwise.
  let execCalled2 = false;
  mm.execOnLoad('a', () => {
    execCalled2 = true;
  });
  assertTrue('module "a" should be loaded', mm.isModuleLoaded('a'));
  assertFalse('module "a" should not be loading', mm.isModuleLoading('a'));
  assertFalse('execCalled2 should not be set yet', execCalled2);
  clock.tick(5);
  assertTrue('execCalled2 should be set', execCalled2);

  // When module is unloaded, execOnLoad is async (user active).
  let execCalled5 = false;
  mm.execOnLoad('c', () => {
    execCalled5 = true;
  }, null, null, true);
  assertFalse('module "c" should not be loaded', mm.isModuleLoaded('c'));
  assertTrue('module "c" should be loading', mm.isModuleLoading('c'));
  assertFalse('execCalled1 should not be set yet', execCalled5);
  assertTrue('ModuleManager should be active', mm.isActive());
  assertTrue('ModuleManager should be user active', mm.isUserActive());
  clock.tick(5);
  assertTrue('module "c" should be loaded', mm.isModuleLoaded('c'));
  assertFalse('module "c" should not be loading', mm.isModuleLoading('c'));
  assertTrue('execCalled1 should be set', execCalled5);
  assertFalse('ModuleManager should not be active', mm.isActive());
  assertFalse('ModuleManager should not be user active', mm.isUserActive());

  // When module is already loaded, execOnLoad is still synchronous when
  // so specified
  let execCalled6 = false;
  mm.execOnLoad('c', () => {
    execCalled6 = true;
  }, undefined, undefined, undefined, true);
  assertTrue('module "c" should be loaded', mm.isModuleLoaded('c'));
  assertFalse('module "c" should not be loading', mm.isModuleLoading('c'));
  assertTrue('execCalled6 should be set', execCalled6);
  clock.tick(5);
  assertTrue('execCalled6 should still be set', execCalled6);
}
Tests execOnLoad with the specified module manager.
@param {ModuleManager} mm The module manager.
@suppress {missingProperties,checkTypes} suppression added to enable type
checking