2 // Copyright (C) 2006 Matthias Braun <matze@braunis.de>
4 // This program is free software: you can redistribute it and/or modify
5 // it under the terms of the GNU General Public License as published by
6 // the Free Software Foundation, either version 3 of the License, or
7 // (at your option) any later version.
9 // This program is distributed in the hope that it will be useful,
10 // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 // GNU General Public License for more details.
14 // You should have received a copy of the GNU General Public License
15 // along with this program. If not, see <http://www.gnu.org/licenses/>.
19 #include "scripting/scripting.hpp"
20 #include "scripting/squirrel_util.hpp"
21 #include "scripting/time_scheduler.hpp"
22 #include "util/log.hpp"
26 TimeScheduler* TimeScheduler::instance = NULL;
28 TimeScheduler::TimeScheduler() :
33 TimeScheduler::~TimeScheduler()
38 TimeScheduler::update(float time)
40 while(!schedule.empty() && schedule.front().wakeup_time < time) {
41 HSQOBJECT thread_ref = schedule.front().thread_ref;
43 sq_pushobject(global_vm, thread_ref);
44 sq_getweakrefval(global_vm, -1);
46 HSQUIRRELVM scheduled_vm;
47 if(sq_gettype(global_vm, -1) == OT_THREAD &&
48 SQ_SUCCEEDED(sq_getthread(global_vm, -1, &scheduled_vm))) {
49 if(SQ_FAILED(sq_wakeupvm(scheduled_vm, SQFalse, SQFalse, SQTrue, SQFalse))) {
50 std::ostringstream msg;
51 msg << "Error waking VM: ";
52 sq_getlasterror(scheduled_vm);
53 if(sq_gettype(scheduled_vm, -1) != OT_STRING) {
57 sq_getstring(scheduled_vm, -1, &lasterr);
60 log_warning << msg.str() << std::endl;
61 sq_pop(scheduled_vm, 1);
65 sq_release(global_vm, &thread_ref);
68 std::pop_heap(schedule.begin(), schedule.end());
74 TimeScheduler::schedule_thread(HSQUIRRELVM scheduled_vm, float time)
76 // create a weakref to the VM
77 SQObject vm_obj = vm_to_object(scheduled_vm);
78 sq_pushobject(global_vm, vm_obj);
79 sq_weakref(global_vm, -1);
82 if(SQ_FAILED(sq_getstackobj(global_vm, -1, & entry.thread_ref))) {
84 throw SquirrelError(global_vm, "Couldn't get thread weakref from vm");
86 entry.wakeup_time = time;
88 sq_addref(global_vm, & entry.thread_ref);
91 schedule.push_back(entry);
92 std::push_heap(schedule.begin(), schedule.end());