int xmain(int argc, char** argv) { DebugGlobalScheduler<EarliestDeadlineFirst> theSim(2); TaskSet ts = TaskSet(); /* ts[0].init(10, 100); ts[1].init(3, 9); ts[2].init(11, 33); ts[3].init(11, 17); ts[4].init(2, 5); */ ts.add_task(20, 30); ts.add_task(20, 30); ts.add_task(20, 30); PeriodicJobSequence* gen[NUM_TASKS]; for (int i = 0; i < NUM_TASKS; i++) { gen[i] = new PeriodicJobSequence(ts[i]); gen[i]->set_simulation(&theSim); theSim.add_release(gen[i]); } theSim.simulate_until(1000); return 0; }
bool BaruahGedf::is_task_schedulable(unsigned int k, const TaskSet &ts, const integral_t &ilen, integral_t &i1, integral_t &sum, integral_t *idiff, integral_t **ptr) { integral_t bound; sum = 0; for (unsigned int i = 0; i < ts.get_task_count(); i++) { interval1(i, k, ts, ilen, i1); interval2(i, k, ts, ilen, idiff[i]); sum += i1; idiff[i] -= i1; } /* sort pointers to idiff to find largest idiff values */ sort(ptr, ptr + ts.get_task_count(), MPZComparator()); for (unsigned int i = 0; i < m - 1 && i < ts.get_task_count(); i++) sum += *ptr[i]; bound = ilen + ts[k].get_deadline() - ts[k].get_wcet(); bound *= m; return sum <= bound; }
void AffinityTask::combinePossibleTaskSet_recursive(const std::unordered_map<CPUID, std::list<TaskSet>>& possibleReplacement, const std::unordered_map<CPUID, CPUID>& nextCPU, const CPUID& currentCPU, const std::list<TaskSet>& visited, std::list<TaskSet>& saveAt) { auto currentList = possibleReplacement.find(currentCPU); auto nextCPUIter = nextCPU.find(currentCPU); if(nextCPUIter == nextCPU.end()) { //time to print for(auto currentItem : currentList->second) { TaskSet returnSet; for(auto curStack : visited) { for(auto task : curStack) returnSet.insert(task); } for(auto task : currentItem) returnSet.insert(task); saveAt.push_back(returnSet); } } else { auto nextCPUID = nextCPUIter->second; for(auto currentItem : currentList->second) { std::list<TaskSet> newVisited(visited); newVisited.push_back(currentItem); combinePossibleTaskSet_recursive( possibleReplacement, nextCPU, nextCPUID, newVisited, saveAt); } } }
std::list<std::list<GraphNode>> AffinityTask::allPath(const TaskSet& taskSet, const GraphNode& start, const GraphNode& target, const Affinity& excludeID, const TaskSet& excludeTask) { std::list<std::list<GraphNode>> returnValue; //prepare link map std::unordered_map<CPUID, TaskSet> cpuToTaskList; std::unordered_map<AffinityTask*, Affinity> taskToCPUList; for(auto task : taskSet) { if(excludeTask.find(task) != excludeTask.end()) continue; Affinity affinityCopy(task->affinity); for(auto cpu : excludeID) affinityCopy.erase(cpu); taskToCPUList.insert(std::pair<AffinityTask*, Affinity>(task, affinityCopy)); for(CPUID cpu : affinityCopy) { if(cpuToTaskList.find(cpu) == cpuToTaskList.end()) cpuToTaskList.insert(std::pair<CPUID, TaskSet>(cpu, TaskSet())); cpuToTaskList.find(cpu)->second.insert(task); } } DFS(returnValue, cpuToTaskList, taskToCPUList, start, target, std::list<GraphNode>()); return returnValue; }
void test_la() { TaskSet ts = TaskSet(); ts.add_task(40, 100, 0, 0, 10, 0); ts.add_task(42, 100, 0, 0, 20, 0); ts.add_task( 2, 100, 50, 0, 5, 0); BakerGedf t = BakerGedf(2); cout << "Baker schedulable? : " << t.is_schedulable(ts) << endl; GFBGedf gfb = GFBGedf(2); cout << "GFB schedulable? : " << gfb.is_schedulable(ts) << endl; cout << "BCL schedulable? : " << BCLGedf(2).is_schedulable(ts) << endl; cout << "Baruah schedulable? : " << BaruahGedf(2).is_schedulable(ts) << endl; cout << "BCL Iter. sched.? : " << BCLIterativeGedf(2).is_schedulable(ts) << endl; cout << "LA schedulable? : " << LAGedf(2).is_schedulable(ts) << endl; cout << "G-EDF schedulable? : " << GlobalEDF(2).is_schedulable(ts) << endl; }
int main(int argc, char **argv) { TaskSet *taskSet; Overhead *overhead; CacheTop *cacheTop; ClusteredTest clusteredTest; SchedTestParam *schedTestParam; CmdlParser cmdlParser(argc, argv); overhead = Overhead::getInstance(); taskSet = new TaskSet(); cacheTop = new CacheTop(); schedTestParam = SchedTestParam::getInstance(); clusteredTest.setTaskSet(taskSet); clusteredTest.setOverhead(overhead); clusteredTest.setCacheTop(cacheTop); schedTestParam->initSchedTestParam(); schedTestParam->setParameters(cmdlParser); schedTestParam->getSchedTestParam(); overhead->updateAllOverheads(schedTestParam); taskSet->updateAllTasks(schedTestParam); cacheTop->updateCacheTop(schedTestParam); taskSet->setParameters(cmdlParser); overhead->setParameters(cmdlParser); clusteredTest.setMHzCpuClock(schedTestParam->getMHzCpuClock()); clusteredTest.makeSchedTest(); return 0; }
void init(const TaskSet &ts, int k, integral_t* bound) { last = -1; dbf = new DBFPointsOfChange[ts.get_task_count()]; for (unsigned int i = 0; i < ts.get_task_count(); i++) { dbf[i].init(ts[i], ts[k]); queue.push(dbf + i); } upper_bound = bound; }
int TaskScheduler::terminateAllTasks() { TaskSet copy = runningThreads; TaskSet::iterator it; PRINTF(1,"Terminating all tasks\n"); for (it = copy.begin();it!=copy.end();it++) { // delete pointer and empty the list of running tasks terminateTask(it->second); } runningThreads.clear(); mainThread.reset(); return 0; }
bool RTAGedf::response_estimate(unsigned int k, const TaskSet &ts, unsigned long const *slack, unsigned long response, unsigned long &new_response) { integral_t other_work = 0; integral_t inf_edf; integral_t inf_rta; integral_t inf_bound = response - ts[k].get_wcet() + 1; integral_t tmp; for (unsigned int i = 0; i < ts.get_task_count(); i++) if (k != i) { edf_interfering_workload(ts[i], ts[k], slack[i], inf_edf); rta_interfering_workload(ts[i], response, slack[i], inf_rta, tmp); other_work += min(min(inf_edf, inf_rta), inf_bound); } /* implicit floor */ other_work /= m; other_work += ts[k].get_wcet(); if (other_work.fits_ulong_p()) { new_response = other_work.get_ui(); return true; } else { /* overflowed => reponse time > deadline */ return false; } }
bool BCLGedf::is_task_schedulable(unsigned int k, const TaskSet &ts) { fractional_t beta_i, beta_sum = 0; fractional_t lambda_term; bool small_beta_exists = false; ts[k].get_density(lambda_term); lambda_term *= -1; lambda_term += 1; for (unsigned int i = 0; i < ts.get_task_count(); i++) { if (i != k) { beta(ts[i], ts[k], beta_i); beta_sum += min(beta_i, lambda_term); small_beta_exists = small_beta_exists || (0 < beta_i && beta_i <= lambda_term); } } lambda_term *= m; return beta_sum < lambda_term || (small_beta_exists && beta_sum == lambda_term); }
void TaskRunner::getReadyTasks(const InitializerTask::SP task, TaskList &readyTasks, TaskSet &checked) { if (task->getState() != State::BLOCKED) { return; // task running or done, all dependencies done } if (!checked.insert(task.get()).second) { return; // task already checked from another depender } const TaskList &deps = task->getDependencies(); bool ready = true; for (const auto &dep : deps) { switch (dep->getState()) { case State::RUNNING: ready = false; break; case State::DONE: break; case State::BLOCKED: ready = false; getReadyTasks(dep, readyTasks, checked); } } if (ready) { readyTasks.push_back(task); } }
bool BCLGedf::is_schedulable(const TaskSet &ts, bool check_preconditions) { if (check_preconditions) { if (!(ts.has_only_feasible_tasks() && ts.is_not_overutilized(m) && ts.has_only_constrained_deadlines())) return false; } for (unsigned int k = 0; k < ts.get_task_count(); k++) if (!is_task_schedulable(k, ts)) return false; return true; }
static void ffdbf_ts(const TaskSet &ts, const integral_t q[], const fractional_t r[], const fractional_t &time, const fractional_t &speed, fractional_t &demand, fractional_t &tmp) { demand = 0; for (unsigned int i = 0; i < ts.get_task_count(); i++) ffdbf(ts[i], time, speed, q[i], r[i], demand, tmp); }
int xxxxmain(int argc, char** argv) { GlobalScheduler<EarliestDeadlineFirst> theSim(24); TaskSet* ts = init_baruah(); PeriodicJobSequence** gen; gen = new PeriodicJobSequence*[ts->get_task_count()]; for (unsigned int i = 0; i < ts->get_task_count(); i++) { gen[i] = new PeriodicJobSequence((*ts)[i]); gen[i]->set_simulation(&theSim); theSim.add_release(gen[i]); } theSim.simulate_until(1000 * 1000 * 1000); // 1000 seconds return 0; }
int main(int argc,char** argv) { if(4 != argc) { cout<<"Usage: ./RMtest [positive processor number] [positive task number] [positive experiment times]"<<endl; return 0; } uint processor_num = atoi(argv[1]); uint task_num = atoi(argv[2]); uint exp_t = atoi(argv[3]); if(0 >= task_num || 0 >= exp_t || 0 >= processor_num) { cout<<"Usage: ./RMtest [positive processor number] [positive task number] [positive experiment times]"<<endl; return 0; } //ProcessorSet processorset = ProcessorSet(processor_num); RMS rms = RMS(processor_num);//uniprocessor uint j = 0; uint success = 0; while(j++ < exp_t) { TaskSet taskset = TaskSet(); for(int i = 1; i <= task_num; i++) { int wcet = int(exponential_gen(5)*100); if(0 == wcet) wcet++; int period = 500; taskset.add_task(wcet,period); } if(rms.is_RM_schedulable(taskset)) success++; } fraction_t rate(success, exp_t); cout << "RM schedulability rate:" << rate << endl; }
int main(int argc, char** argv) { char tempFile [] = "tempFile.txt"; TaskSetInputParser parser; stringstream csvFileName; csvFileName << "datapoints_number_tasks_" << NUMBER_OF_TASKS; ofstream outputFile; outputFile.open((char*)csvFileName.str().c_str()); Simulator s; for (double currentIncrement = 0.1; currentIncrement<=0.9; currentIncrement+=0.1) { outputFile << currentIncrement << ","; TaskGenerator::generateTasksAndWriteToFile(tempFile, currentIncrement, NUMBER_OF_TASKS, NUMBER_OF_TASKS_SETS); parser.parseInputFile(tempFile); int totalTaskSets = parser.getTaskSetSize(); while(!parser.isEmpty()) { TaskSet taskSet = parser.getNext(); cout << "<Analyzing task set> \n"; taskSet.printTaskSet(); cout << "\n"; taskSet.sortTaskSetByUtilization(); outputFile << s.MUF(taskSet) << ","; taskSet.sortTaskSetByPeriod(); outputFile << s.RM(taskSet) << ","; taskSet.sortTaskSetByWCET(); outputFile << s.SJF(taskSet) << "\n";; } } return 0; }
bool RTAGedf::is_schedulable(const TaskSet &ts, bool check_preconditions) { if (check_preconditions) { if (!(ts.has_only_feasible_tasks() && ts.is_not_overutilized(m) && ts.has_only_constrained_deadlines() && ts.has_only_feasible_tasks())) return false; if (ts.get_task_count() == 0) return true; } unsigned long* slack = new unsigned long[ts.get_task_count()]; for (unsigned int i = 0; i < ts.get_task_count(); i++) slack[i] = 0; unsigned long round = 0; bool schedulable = false; bool updated = true; while (updated && !schedulable && (max_rounds == 0 || round < max_rounds)) { round++; schedulable = true; updated = false; for (unsigned int k = 0; k < ts.get_task_count(); k++) { unsigned long response, new_slack; if (rta_fixpoint(k, ts, slack, response)) { new_slack = ts[k].get_deadline() - response; if (new_slack != slack[k]) { slack[k] = new_slack; updated = true; } } else { schedulable = false; } } } return schedulable; }
void SchedViz::Visit_Node( const Semantics::Node &node ) { std::string nodeName = node.name(); DBGOUT("Node: " << nodeName << std::endl) // Add a superblock to the viz TVSuperblock* superblock = this->_traceViz->AddSuperblock( nodeName, this->_hyperperiodSec ); // Now iterate through all of the task children TaskSet taskSet = node.executes(); TaskSet::iterator taskIter = taskSet.begin(); for ( ; taskIter != taskSet.end(); taskIter++ ) { // Visit the task this->Visit_Task( *taskIter, superblock ); } // Now interate through all of the device children DeviceSet deviceSet = node.integrates(); DeviceSet::iterator deviceIter = deviceSet.begin(); for ( ; deviceIter != deviceSet.end(); deviceIter++ ) { // Visit the device this->Visit_Device( *deviceIter, superblock ); } }
bool BCLIterativeGedf::slack_update(unsigned int k, const TaskSet &ts, unsigned long *slack, bool &has_slack) { integral_t other_work = 0; integral_t inf; integral_t inf_bound = ts[k].get_deadline() - ts[k].get_wcet() + 1; for (unsigned int i = 0; i < ts.get_task_count(); i++) if (k != i) { interfering_workload(ts[i], ts[k], slack[i], inf); other_work += min(inf, inf_bound); } other_work /= m; unsigned long tmp = ts[k].get_wcet() + other_work.get_ui(); assert( other_work.fits_ulong_p() ); assert (tmp > other_work.get_ui() ); has_slack = tmp <= ts[k].get_deadline(); if (!has_slack) // negative slack => no update, always assume zero return false; else { tmp = ts[k].get_deadline() - tmp; if (tmp > slack[k]) { // better slack => update slack[k] = tmp; return true; } else // no improvement return false; } }
bool BCLIterativeGedf::is_schedulable(const TaskSet &ts, bool check_preconditions) { if (check_preconditions) { if (!(ts.has_only_feasible_tasks() && ts.is_not_overutilized(m) && ts.has_only_constrained_deadlines())) return false; if (ts.get_task_count() == 0) return true; } unsigned long* slack = new unsigned long[ts.get_task_count()]; for (unsigned int i = 0; i < ts.get_task_count(); i++) slack[i] = 0; unsigned long round = 0; bool schedulable = false; bool updated = true; while (updated && !schedulable && (max_rounds == 0 || round < max_rounds)) { round++; schedulable = true; updated = false; for (unsigned int k = 0; k < ts.get_task_count(); k++) { bool ok; if (slack_update(k, ts, slack, ok)) updated = true; schedulable = schedulable && ok; } } return schedulable; }
bool GFBGedf::is_schedulable(const TaskSet &ts, bool check_preconditions) { if (check_preconditions) { if (!(ts.has_only_feasible_tasks() && ts.is_not_overutilized(m) && ts.has_only_constrained_deadlines() && ts.has_no_self_suspending_tasks())) return false; } fractional_t total_density, max_density, bound; ts.get_density(total_density); ts.get_max_density(max_density); bound = m - (m - 1) * max_density; return total_density <= bound; }
void BaruahGedf::get_max_test_points(const TaskSet &ts, fractional_t &m_minus_u, integral_t* maxp) { unsigned long* wcet = new unsigned long[ts.get_task_count()]; for (unsigned int i = 0; i < ts.get_task_count(); i++) wcet[i] = ts[i].get_wcet(); sort(wcet, wcet + ts.get_task_count(), greater<unsigned long>()); fractional_t u, tdu_sum; integral_t csigma, mc; csigma = 0; for (unsigned int i = 0; i < m - 1 && i < ts.get_task_count(); i++) csigma += wcet[i]; tdu_sum = 0; for (unsigned int i = 0; i < ts.get_task_count(); i++) { ts[i].get_utilization(u); tdu_sum += (ts[i].get_period() - ts[i].get_deadline()) * u; } for (unsigned int i = 0; i < ts.get_task_count(); i++) { mc = ts[i].get_wcet(); mc *= m; mc += 0.124; maxp[i] = (csigma - (ts[i].get_deadline() * m_minus_u) + tdu_sum + mc) / m_minus_u; } delete wcet; }
bool FFDBFGedf::is_schedulable(const TaskSet &ts, bool check_preconditions) { if (m < 2) return false; if (check_preconditions) { if (!(ts.has_only_feasible_tasks() && ts.is_not_overutilized(m) && ts.has_only_constrained_deadlines() && ts.has_no_self_suspending_tasks())) return false; } // allocate helpers AllTestPoints testing_set(ts); integral_t *q = new integral_t[ts.get_task_count()]; fractional_t *r = new fractional_t[ts.get_task_count()]; fractional_t sigma_bound; fractional_t time_bound; fractional_t tmp(1, epsilon_denom); // compute sigma bound tmp = 1; tmp /= epsilon_denom; ts.get_utilization(sigma_bound); sigma_bound -= m; sigma_bound /= - ((int) (m - 1)); // neg. to flip sign sigma_bound -= tmp; // epsilon sigma_bound = min(sigma_bound, fractional_t(1)); // compute time bound time_bound = 0; for (unsigned int i = 0; i < ts.get_task_count(); i++) time_bound += ts[i].get_wcet(); time_bound /= tmp; // epsilon fractional_t t_cur; fractional_t sigma_cur, sigma_nxt; bool schedulable; t_cur = 0; schedulable = false; // Start with minimum possible sigma value, then try // multiples of sigma_step. ts.get_max_density(sigma_cur); // setup brute force sigma value range sigma_nxt = sigma_cur / sigma_step; truncate_fraction(sigma_nxt); sigma_nxt += 1; sigma_nxt *= sigma_step; while (!schedulable && sigma_cur <= sigma_bound && t_cur <= time_bound) { testing_set.init(sigma_cur, t_cur); do { testing_set.get_next(t_cur); if (t_cur <= time_bound) { compute_q_r(ts, t_cur, q, r); schedulable = witness_condition(ts, q, r, t_cur, sigma_cur); } else // exceeded testing interval schedulable = true; } while (t_cur <= time_bound && schedulable); if (!schedulable && t_cur <= time_bound) { // find next sigma variable do { sigma_cur = sigma_nxt; sigma_nxt += sigma_step; } while (sigma_cur <= sigma_bound && !witness_condition(ts, q, r, t_cur, sigma_cur)); } } delete [] q; delete [] r; return schedulable; }
AllTestPoints(const TaskSet &ts) : ts(ts) { pts = new TestPoints[ts.get_task_count()]; }
bool AffinityTask::staticStrongAnalysis(const TaskSet& taskSet, Time overhead) { AffinityTask::Compare compare; std::unordered_map<AffinityTask*, Time> responseTime; Affinity allCPU; for(AffinityTask* task : taskSet) { responseTime.insert(std::pair<AffinityTask*, Time>(task, task->worstExecution)); for(auto cpu : task->affinity) allCPU.insert(cpu); } while(true) { bool changed = false; bool overflow = false; std::unordered_map<AffinityTask*, Time> newResponseTime; for(auto current : responseTime) { AffinityTask* curTask = current.first; std::set<Affinity> powerSet = AffinityTask::powerSet(curTask->affinity); Time currentResponse = responseTime.find(curTask)->second; TaskSet ignoreTask; ignoreTask.insert(curTask); Time min_sumInterfere = std::numeric_limits<Time>::max(); for(Affinity s : powerSet) { assert(s.size() != 0); Size s_Size = s.size(); //Time sumInterference = 0; std::unordered_map<CPUID, std::list<TaskSet>> possibleReplacement; for(auto cpu : s) { possibleReplacement.insert(std::pair<CPUID, std::list<TaskSet>> (cpu, std::list<TaskSet>())); } for(CPUID selectedCPU : s) { Affinity ignoreCPU(s); ignoreCPU.erase(selectedCPU); for(auto alternative : allCPU) { if(ignoreCPU.find(alternative) != ignoreCPU.end()) continue; auto allPaths = allPath(taskSet, selectedCPU, alternative, ignoreCPU, ignoreTask); for(auto path : allPaths) { if(path.size() > 0) { TaskSet ignoredTask; Affinity moreCheck; for(auto item : path) { if(item.isTask()) ignoredTask.insert(item.getTask()); else moreCheck.insert(item.getCPUID()); } TaskSet highTaskSet; for(AffinityTask* highPriorityTask : taskSet) { //if(compare(curTask, highPriorityTask)) // continue; if(highPriorityTask == curTask) continue; if(ignoredTask.find(highPriorityTask) != ignoredTask.end()) continue; bool intersect = false; for(auto cpu : highPriorityTask->affinity) { if(moreCheck.find(cpu) != moreCheck.end()) { intersect = true; break; } } if(!intersect) continue; highTaskSet.insert(highPriorityTask); } possibleReplacement.find(selectedCPU)->second.push_back(highTaskSet); } } } } for(auto possibleSet : combinePossibleTaskSet(possibleReplacement)) { Time sumInterference = 0; /* if(possibleSet.size() ==0) continue; assert(possibleSet.size() > 0); */ sumInterference += overhead; for(auto highPriorityTask : possibleSet) { Time interferenceCount = currentResponse/highPriorityTask->minPeriod; Time remaining = currentResponse % highPriorityTask->minPeriod; Time interference = interferenceCount * highPriorityTask->worstExecution + std::min(remaining, highPriorityTask->worstExecution); Time contextSwitchCount = interferenceCount; if(remaining > 0) contextSwitchCount++; sumInterference += 2*(contextSwitchCount) * overhead; if(compare(curTask, highPriorityTask)) continue; sumInterference += interference; } Time floorValue = floor((Real)sumInterference / (Real)s_Size); min_sumInterfere = std::min(min_sumInterfere, floorValue); } } assert(min_sumInterfere != std::numeric_limits<Time>::max()); Time nextResponse = curTask->worstExecution + min_sumInterfere; newResponseTime.insert(std::pair<AffinityTask*, Time>(curTask, nextResponse)); if(currentResponse != nextResponse) changed = true; if(currentResponse > curTask->minPeriod) overflow = true; } if(changed) responseTime = newResponseTime; else break; if(overflow) break; } bool possible = true; for(auto iter : responseTime) { if(iter.second > iter.first->minPeriod) { possible = false; iter.first->print_log(WARN, "Execution time: %lu, Period: %lu, Response time: %lu", iter.first->worstExecution, iter.first->minPeriod, iter.second); } else { iter.first->print_log(INFO, "Execution time: %lu, Period: %lu, Response time: %lu", iter.first->worstExecution, iter.first->minPeriod, iter.second); } } return possible; }
bool BaruahGedf::is_schedulable(const TaskSet &ts, bool check_preconditions) { if (check_preconditions) { if (!(ts.has_only_feasible_tasks() && ts.is_not_overutilized(m) && ts.has_only_constrained_deadlines())) return false; if (ts.get_task_count() == 0) return true; } fractional_t m_minus_u; ts.get_utilization(m_minus_u); m_minus_u *= -1; m_minus_u += m; if (m_minus_u <= 0) { // Baruah's G-EDF test requires strictly positive slack. // In the case of zero slack the testing interval becomes // infinite. Therefore, we can't do anything but bail out. return false; } double start_time = get_cpu_usage(); integral_t i1, sum; integral_t *max_test_point, *idiff; integral_t** ptr; // indirect access to idiff idiff = new integral_t[ts.get_task_count()]; max_test_point = new integral_t[ts.get_task_count()]; ptr = new integral_t*[ts.get_task_count()]; for (unsigned int i = 0; i < ts.get_task_count(); i++) ptr[i] = idiff + i; get_max_test_points(ts, m_minus_u, max_test_point); integral_t ilen; bool point_in_range = true; bool schedulable = true; AllDBFPointsOfChange *all_pts; all_pts = new AllDBFPointsOfChange[ts.get_task_count()]; for (unsigned int k = 0; k < ts.get_task_count() && schedulable; k++) all_pts[k].init(ts, k, max_test_point + k); // for every task for which point <= max_ak unsigned long iter_count = 0; while (point_in_range && schedulable) { point_in_range = false; // check for excessive run time every 10 iterations if (++iter_count % 10 == 0 && get_cpu_usage() > start_time + MAX_RUNTIME) { // This is taking too long. Give up. schedulable = false; break; } for (unsigned int k = 0; k < ts.get_task_count() && schedulable; k++) if (all_pts[k].get_next(ilen)) { schedulable = is_task_schedulable(k, ts, ilen, i1, sum, idiff, ptr); point_in_range = true; } } delete[] all_pts; delete[] max_test_point; delete[] idiff; delete[] ptr; return schedulable; }
void AffinityTask::cleanTaskSet(TaskSet& taskSet) { for(AffinityTask* task : taskSet) delete task; taskSet.clear(); }
static void compute_q_r(const TaskSet &ts, const fractional_t &time, integral_t q[], fractional_t r[]) { for (unsigned int i = 0; i < ts.get_task_count(); i++) get_q_r(ts[i], time, q[i], r[i]); }
bool AffinityTask::staticWeakAnalysis(const TaskSet& taskSet, Time overhead) { AffinityTask::Compare compare; std::unordered_map<AffinityTask*, Time> responseTime; for(AffinityTask* task : taskSet) responseTime.insert(std::pair<AffinityTask*, Time>(task, task->worstExecution)); while(true) { bool changed = false; bool overflow = false; std::unordered_map<AffinityTask*, Time> newResponseTime; for(auto current : responseTime) { AffinityTask* curTask = current.first; std::set<Affinity> powerSet = AffinityTask::powerSet(curTask->affinity); Time currentResponse = responseTime.find(curTask)->second; Time min_sumInterfere = std::numeric_limits<Time>::max(); for(Affinity s : powerSet) { assert(s.size() != 0); Size s_Size = s.size(); Time sumInterference = 0; Time localSum = 0; TaskSet highPrioritySet; for(CPUID selectedCPU : s) { for(AffinityTask* highPriorityTask : taskSet) { if(compare(curTask, highPriorityTask)) continue; if(highPriorityTask == curTask) continue; if(highPriorityTask->affinity.find(selectedCPU) == highPriorityTask->affinity.end()) continue; highPrioritySet.insert(highPriorityTask); } } localSum += overhead; for(AffinityTask* highPriorityTask : highPrioritySet) { Time interferenceCount = currentResponse/highPriorityTask->minPeriod; Time remaining = currentResponse % highPriorityTask->minPeriod; Time interference = interferenceCount * highPriorityTask->worstExecution + std::min(remaining, highPriorityTask->worstExecution); localSum += interference; Time contextSwitchCount = interferenceCount; if(remaining > 0) contextSwitchCount++; localSum += 2*(contextSwitchCount) * overhead; } sumInterference += localSum; Time floorValue = floor((Real)sumInterference / (Real)s_Size); min_sumInterfere = std::min(min_sumInterfere, floorValue); } assert(min_sumInterfere != std::numeric_limits<Time>::max()); Time nextResponse = curTask->worstExecution + min_sumInterfere; newResponseTime.insert(std::pair<AffinityTask*, Time>(curTask, nextResponse)); if(currentResponse != nextResponse) changed = true; if(currentResponse > curTask->minPeriod) overflow = true; } if(changed) responseTime = newResponseTime; else break; if(overflow) break; } bool possible = true; for(auto iter : responseTime) { if(iter.second > iter.first->minPeriod) { possible = false; iter.first->print_log(WARN, "Execution time: %lu, Period: %lu, Response time: %lu", iter.first->worstExecution, iter.first->minPeriod, iter.second); } else { iter.first->print_log(INFO, "Execution time: %lu, Period: %lu, Response time: %lu", iter.first->worstExecution, iter.first->minPeriod, iter.second); } } return possible; }
void TrueTimeSourceVisitor::Visit_Node( const Semantics::Node & node ) { // Setup the node name std::string kernelName = node.name(); std::string kernelInitName = kernelName + "_init"; DEBUGOUT( "\tNode: " << kernelName << std::endl ); // Must be the second pass _SchedHeaderLines.push_back( string( "// Define Schedule Offsets and Durations" ) ); _SchedHeaderLines.push_back( string( "" ) ); // Create the file name std::string filename = std::string( node.name() ) + "_init"; // Create the hyperperiod symbol string for the node std::string hyp_str = kernelName + "_HYPERPERIOD"; // Set some dictionary items for this node GetMainDictionary().SetValue( "FILENAME", filename ); GetMainDictionary().SetValue( "KERNEL_SCHEDULE", "prioFP" ); GetMainDictionary().SetFormattedValue( "KERNEL_HYPERPERIOD", "%f", (double) node.hyperperiodsecs() ); GetMainDictionary().SetValue( "NODE_HYPERPERIOD_STR", hyp_str ); DeviceSet devices = node.integrates(); for ( DeviceSet::iterator devIter = devices.begin(); devIter != devices.end(); devIter++ ) { if ( (*devIter).type() == Semantics::CommInterface::meta ) { Semantics::CommInterface ci = Semantics::CommInterface::Cast( *devIter ); Semantics::CommMedium cm = ci.commMedium(); if ( cm != Udm::null ) { string busname = cm.name(); AddSectionDictionary( "BUS_DEFINES" ); GetTemplateDictionary().SetValue( "BUSNAME", busname ); PopSectionDictionary(); } } } if ( _SchedHeaderLines.size() < 4 ) { ostringstream out; out << "#define " << hyp_str << " " << (double)node.hyperperiodsecs(); _SchedHeaderLines.push_back( out.str() ); } _already_included.clear(); // clear include list for each node // Visit all tasks assigned to this node TaskSet taskSet = node.executes(); TaskVector taskVector( taskSet.begin(), taskSet.end() ); TaskVector::iterator taskIter = taskVector.begin(); for ( ; taskIter != taskVector.end(); taskIter++ ){ // Visit the task taskIter->Accept( *this ); } // Clear the analog in/out counters _analogIn = 1; _analogOut = 1; // Set up a sorted list of IChans and OChans SortedIChan_ByChanIndex_Set ichans; SortedOChan_ByChanIndex_Set ochans; // Visit all devices contained in this node DeviceSet deviceSet = node.integrates(); DeviceSet::iterator deviceIter = deviceSet.begin(); for ( ; deviceIter != deviceSet.end(); deviceIter++ ) { // Collect all of the IChans and OChans, and keep them in the proper sorted order // See if device is input if ( Semantics::InputDevice::meta == (*deviceIter).type() ) { // Cast to an InputDevice Semantics::InputDevice input = Semantics::InputDevice::Cast( *deviceIter ); // Get the associated IChans SortedIChan_ByChanIndex_Set iChanSet = input.inputChannels_sorted( IChanIndexSorter() ); ichans.insert( iChanSet.begin(), iChanSet.end() ); } // See if device is output else if ( Semantics::OutputDevice::meta == (*deviceIter).type() ) { // Cast to an InputDevice Semantics::OutputDevice output = Semantics::OutputDevice::Cast( *deviceIter ); // Get the associated OChans SortedOChan_ByChanIndex_Set oChanSet = output.outputChannels_sorted( OChanIndexSorter() ); ochans.insert( oChanSet.begin(), oChanSet.end() ); } } // Now process the IChans and OChans in order IChanVector iChanVector( ichans.begin(), ichans.end() ); for ( IChanVector::iterator ichanIter = iChanVector.begin(); ichanIter != iChanVector.end(); ichanIter++ ) { ichanIter->Accept( *this ); } OChanVector oChanVector( ochans.begin(), ochans.end() ); for ( OChanVector::iterator ochanIter = oChanVector.begin(); ochanIter != oChanVector.end(); ochanIter++ ) { ochanIter->Accept( *this ); } // Visit all local dependencies on this node LocalDependencySet dependencySet = node.nodeLocalDeps(); LocalDependencyVector dependencyVector( dependencySet.begin(), dependencySet.end() ); LocalDependencyVector::iterator dependencyIter = dependencyVector.begin(); for ( ; dependencyIter != dependencyVector.end(); dependencyIter++ ) { // Visit the dependency dependencyIter->Accept( *this ); } // Visit the dummy dependency message on this node (if we have one) Semantics::Msg dummyMsg = node.nodeDummyMsg(); if ( dummyMsg != Udm::null ) Visit_DummyMessage( dummyMsg ); // Get the template file name std::string templateName = ConfigKeeper::inst().GetTemplatePath() + "\\truetime_src.tpl"; // Initialize the template ctemplate::Template* googleTemplate = ctemplate::Template::GetTemplate( templateName, ctemplate::DO_NOT_STRIP ); std::string output; // Expand the output into a string googleTemplate->Expand( &output, &GetMainDictionary() ); // Create the _init file for this TT kernel std::string directoryName = ConfigKeeper::inst().GetDirectoryName(); string srcfilename = directoryName + "\\" + filename + ".cpp"; ofstream initFile( srcfilename.c_str() ); // Write the generated code out to the file and close initFile << output; // Close up the file initFile.close(); // Clear out the dictionary ClearDictionary(); // Write out the header file for the defines string hdrfilename = directoryName + "\\" + filename + "_defines.h"; cout << "Writing header: " << hdrfilename << endl; ofstream headerFile( hdrfilename.c_str() ); for ( std::vector< std::string >::iterator lineIter = _SchedHeaderLines.begin(); lineIter != _SchedHeaderLines.end(); lineIter++ ) { headerFile << *lineIter << endl; } headerFile.close(); _SchedHeaderLines.clear(); // flush the list }