void init() {

  // Initialize TrueTime kernel  
  ttInitKernel(1, 0, prioFP); // nbrOfInputs, nbrOfOutputs, fixed priority
  
  // Create task data (local memory)
  data = new PD_Data;
  data->K = 1.5;
  data->Td = 0.035;
  data->N = 100000.0;
  data->h = 0.010;
  data->ad = data->Td/(data->N*data->h+data->Td);
  data->bd = data->N*data->K*data->Td/(data->N*data->h+data->Td);
  data->yold = 0.0;
  data->Dold = 0.0;
  data->u = 0.0;

  // Controller task
  double deadline = 0.010;
  double prio = 2.0;
  ttCreateTask("pid_task", deadline, prio, ctrl_code, data);
  ttCreateJob("pid_task");

  // Disturbance task (uncomment to add disturbance task)
  // double offset = 0.0002;
  // double period = 0.007;
  // prio = 1.0;
  // ttCreatePeriodicTask("dummy", offset, period, prio, dummy_code);

  // Initialize network
  ttCreateInterruptHandler("msgRcv", prio, msgRcvhandler);
  ttInitNetwork(3, "msgRcv"); // node #3 in the network
  
  ttCreateSemaphore("sem", 0);
}
Esempio n. 2
0
void ttCreateTask(char *name, double deadline, double priority, double (*codeFcn)(int, void*), void* data) {

  DataNode *n;

  if (ttCreateTask(name, deadline, priority, codeFcn)) {
    n = (DataNode*) rtsys->taskList->getLast();
    ((Task*) n->data)->data = data;
  } 
}
Esempio n. 3
0
bool ttCreatePeriodicTask(char *name, double offset, double period, double priority, double (*codeFcn)(int, void*)) {

  DataNode* dn;
  InterruptHandler* hdl;
  Timer *t;
  
  if (ttCreateTask(name, period, priority, codeFcn)) {

    dn = (DataNode*) rtsys->taskList->getLast(); // last created task

    // Create interrupt handler invoked periodically to create task jobs
    // see codefunctions.cpp for the code function
    hdl = new InterruptHandler("perHandler");
    hdl->codeFcn = rtsys->periodicTaskHandlerCode;

    hdl->handlerID = rtsys->nbrOfHandlers + 1;
    hdl->priority = -1000.0;
    hdl->display = false;
    hdl->data = (UserTask*) dn->data;

    rtsys->handlerList->appendNode(new DataNode(hdl, NULL));
    rtsys->nbrOfHandlers++;

    // Creating periodic timer that triggers the handler
    t = new Timer("perTimer");
    t->time = offset;  // First timer expiry at task offset
    t->period = period;
    t->isPeriodic = true;

    hdl->timer = t;
    hdl->moveToList(rtsys->timeQ);
    hdl->type = TIMER;
    
    ((UserTask*) dn->data)->periodichandler = hdl;
    return true;
  } else {
    return false;
  }
}
Esempio n. 4
0
void init() {

  // Read the input argument from the block dialogue
  mxArray *initarg = ttGetInitArg();
  if (!mxIsDoubleScalar(initarg)) {
    TT_MEX_ERROR("The init argument must be a number!\n");
    return;
  }
  int implementation = (int)mxGetPr(initarg)[0];

  // Allocate KernelData memory and store pointer in kernel
  KernelData *kd = new KernelData;
  ttSetUserData(kd);

  // Allocate memory for implementation != 2
  TaskData *d = new TaskData;
  kd->d = d;  // Store pointer in KernelData

  // Allocate memory for implementation 2
  double *d2 = new double;
  kd->d2 = d2; // Store pointer in KernelData

  // Allocate memory for implementation 4
  int *hdl_data = new int;
  kd->hdl_data = hdl_data;   // Store pointer in KernelData
  
  // Initialize TrueTime kernel
  ttInitKernel(prioFP);

  // Task attributes
  double starttime = 0.0;
  double period = 0.006;
  double deadline = period;

  // Controller parameters and states
  d->K = 0.96;
  d->Ti = 0.12;
  d->Td = 0.049;
  d->beta = 0.5;
  d->N = 10.0;
  d->h = period;
  d->u = 0.0;
  d->t = 0.0;  // only used for implementation 3
  d->Iold = 0.0;
  d->Dold = 0.0;
  d->yold = 0.0;
  d->rChan = 1;
  d->yChan = 2;
  d->uChan = 1;

  switch (implementation) {
    
  case 1:
    // IMPLEMENTATION 1: using the built-in support for periodic tasks
    
    ttCreatePeriodicTask("pid_task", starttime, period, pid_code1, d);
    
    break;

  case 2:
    // IMPLEMENTATION 2: calling Simulink block within code function
    
    ttCreatePeriodicTask("pid_task", starttime, period, pid_code2, d2);
    break;

  case 3:
    // IMPLEMENTATION 3: sleepUntil and loop back
  
    ttCreateTask("pid_task", deadline, pid_code3, d);
    ttCreateJob("pid_task");
    break;
    
  case 4:
    // IMPLEMENTATION 4: sampling in timer handler, triggers task job
  
    *hdl_data = 2; // y_chan for reading samples
    ttCreateHandler("timer_handler", 1, sampler_code, hdl_data);
    ttCreatePeriodicTimer("timer", starttime, period, "timer_handler");
    ttCreateMailbox("Samples", 10);
    ttCreateTask("pid_task", deadline, pid_code4, d);
    break;

  }
}
Esempio n. 5
0
void mexFunction( int nlhs, mxArray *plhs[],
                  int nrhs, const mxArray *prhs[] )
{
  rtsys = getrtsys() ; // Get pointer to rtsys 

  if (rtsys==NULL) {
    return;
  }

  // Check number and type of arguments. 
  if (nrhs < 4 || nrhs > 5) {
    MEX_ERROR("ttCreateTask: Wrong number of input arguments! \nUsage: ttCreateTask(name, deadline, priority, codefcn)\n       ttCreateTask(name, deadline, priority, codefcn, data)");
    return;
  }

  if (mxIsChar(prhs[0]) != 1) {
    MEX_ERROR("ttCreateTask: name must be a string");
    return;
  }
  if (!mxIsDoubleScalar(prhs[1])) {
    MEX_ERROR("ttCreateTask: deadline must be a double scalar");
    return;
  }
  if (!mxIsDoubleScalar(prhs[2])) {
    MEX_ERROR("ttCreateTask: priority must be a double scalar");
    return;
  }
  if (mxIsChar(prhs[3]) != 1 || mxGetM(prhs[3]) != 1) {
    MEX_ERROR("ttCreateTask: codeFcn must be a non-empty string");
    return;
  }
  
  char name[100];
  mxGetString(prhs[0], name, 100);
  
  double deadline = *mxGetPr(prhs[1]);
  if (deadline < -EPS) {
    deadline = 0.0;
    printf("ttCreateTask: negative deadline changed to zero\n");
  }

  double priority = *mxGetPr(prhs[2]);

  char codeFcn[100];
  mxGetString(prhs[3], codeFcn, 100);

  // Make sure that the code function exists in Matlab path
  // and that the code function is syntactically correct.
  mxArray *lhs[1];
  mxArray *rhs[1];
  rhs[0] = mxDuplicateArray(prhs[3]);
  mexCallMATLAB(1, lhs, 1, rhs, "exist");
  int number = (int) *mxGetPr(lhs[0]);
  if (number == 0) {
    char buf[200];
    sprintf(buf, "ttCreateTask: codeFcn '%s' not in path! Task '%s' not created!", codeFcn, name);
    MEX_ERROR(buf);
    return;
  }

  if (ttCreateTask(name, deadline, priority, NULL)) {
  
    // Add name of code function (m-file) and data variable
    DataNode *n = (DataNode*) rtsys->taskList->getLast();
    UserTask *usertask = (UserTask*) n->data;
    
    usertask->codeFcnMATLAB = new char[strlen(codeFcn)+1];
    strcpy(usertask->codeFcnMATLAB, codeFcn);
    
    mxArray* data;
    if (nrhs == 4) { // no data specified
      data = mxCreateDoubleMatrix(0, 0, mxREAL);
    } else {
      data = mxDuplicateArray((mxArray*)prhs[4]);
    }
    mexMakeArrayPersistent(data);
    usertask->dataMATLAB = data;
  }
}