1function model = JSIM2LINE(filename,modelName)
2% MODEL = JSIM2LINE(FILENAME,MODELNAME)
4% Copyright (c) 2012-2026, Imperial College London
8Pref.Str2Num = 'always';
9xDoc = xml_read(filename,Pref);
16 [~,modelName] = fileparts(xDoc.ATTRIBUTE.name);
18model = Network(modelName);
21node_name = cellfun(@(x) x.name, {xDoc.node.ATTRIBUTE},
'UniformOutput',
false)
';
22orig_node_name = node_name;
23for i=1:length(node_name)
24 node_name{i}=strrep(node_name{i},'/
','_
');
25 node_name{i}=strrep(node_name{i},'\
','_
');
28xsection = {xDoc.node.section};
29strategy = cell(1,length(node_name));
32xsection_javaClass = {};
36% This is to create the cs elements last, unclear if it affects correctness
37% isStation = ones(1,length(node_name));
38% for i=1:length(node_name)
39% xsection_i{i} = {xsection{i}};
40% xsection_i{i} = xsection_i{i}{1}; % input, service, and output sections of node i
41% xsection_class{i} = {xsection_i{i}.ATTRIBUTE};
42% switch xsection_class{i}{1}.className % input section
44% xsection_i_type{i} = {xsection{i}.ATTRIBUTE};
45% switch xsection_i_type{i}{2}.className
46% case {'StatelessClassSwitcher
'}
52%for i=[find(isStation==1), find(isStation==0)]
53for i=1:length(node_name)
54 xsection_i{i} = {xsection{i}};
55 xsection_i{i} = xsection_i{i}{1}; % input, service, and output sections of node i
56 xsection_javaClass{i} = {xsection_i{i}.ATTRIBUTE};
57 switch xsection_javaClass{i}{1}.className % input section
59 node{i} = Sink(model, node_name{i});
62 node{i} = Source(model, node_name{i});
64 xrouting{i} = {xsection_i{i}(3).parameter.subParameter.ATTRIBUTE};
67 forkMap=find(cellfun(@any,strfind(cellfun(@class,model.nodes,'UniformOutput
',false),'Fork
')));
69 line_error(mfilename,'JSIM2LINE supports at most a single fork-join pair.
');
71 node{i} = Join(model, node_name{i}, node{forkMap});
72 xrouting{i} = {xsection_i{i}(3).parameter.subParameter.ATTRIBUTE};
74 switch xsection_javaClass{i}{3}.className
76 node{i} = Fork(model, node_name{i});
77 node{i}.setTasksPerLink(xsection_i{i}(3).parameter(1).value); %jobsPerLink
78 xrouting{i} = {xsection_i{i}(3).parameter(4).subParameter.ATTRIBUTE};
80 switch xsection_javaClass{i}{2}.className
82 node{i} = Router(model, node_name{i});
83 xrouting{i} = {xsection_i{i}(3).parameter.subParameter.ATTRIBUTE};
85 xsection_par{i} = {xsection{i}.parameter};
86 xsection_i_par{i} = xsection_i{i}.parameter;
88 xsection_i_value{i} = {xsection_i_par{i}.value};
89 xsection_i_par_attr{i} = {xsection_i_par{i}.ATTRIBUTE};
91 xsection_i_subpar{i} = {xsection_i_par{i}.subParameter};
92 %if xsection_i_value{i}{1}==-1
93 % node{i} = Router(model, node_name{i});
96 xsvc{i} = {xsection_i{i}(2).parameter.subParameter};
97 xrouting{i} = {xsection_i{i}(3).parameter.subParameter.ATTRIBUTE};
99 % xget_strategy{i} = {xsection_i_par{i}.ATTRIBUTE};
100 % switch xget_strategy{i}{3}.name
101 % case 'LCFSstrategy
'
102 % strategy{i} = SchedStrategy.LCFS;
103 % case 'FCFSstrategy
'
104 % strategy{i} = SchedStrategy.FCFS;
107 xput_strategy{i} = xsection_i_par{i};
108 switch xput_strategy{i}(3).ATTRIBUTE.name
109 case 'retrialDistributions
'
110 % new XML format from 1.2.0
111 %xretrial_strategy{i}= {xput_strategy{i}(4)};
112 xput_strategy{i}= {xput_strategy{i}(5).subParameter.ATTRIBUTE};
114 xput_strategy{i}= {xput_strategy{i}(4).subParameter.ATTRIBUTE};
116 switch xput_strategy{i}{1}.name
118 strategy{i} = SchedStrategy.FCFS;
119 case 'TailStrategyPriority
'
120 strategy{i} = SchedStrategy.HOL;
122 strategy{i} = SchedStrategy.LCFS;
124 strategy{i} = SchedStrategy.SIRO;
126 strategy{i} = SchedStrategy.SJF;
128 strategy{i} = SchedStrategy.SEPT;
130 strategy{i} = SchedStrategy.LJF;
132 strategy{i} = SchedStrategy.LEPT;
135 xsection_i_type{i} = {xsection{i}.ATTRIBUTE};
136 switch xsection_i_type{i}{2}.className
138 node{i} = Delay(model, node_name{i});
139 xcapacity = {xsection_i_par{i}.value};
140 node{i}.setCapacity(xcapacity{1}); % buffer size
142 node{i} = Queue(model, node_name{i}, strategy{i});
143 xcapacity = {xsection_i_par{i}.value};
144 node{i}.setCapacity(xcapacity{1}); % buffer size
145 xsection_par_val{i} = {xsection_par{end}{2}.value};
146 node{i}.setNumServers(xsection_par_val{i}{1});
147 switch SchedStrategy.toId(strategy{i})
148 case SchedStrategy.SEPT
149 schedparams{i} = NaN;
151 case 'PSServer
' % requires JMT >= 1.0.2
152 strategy_i_sub={xsection_par{i}{2}.subParameter};
153 strategy_i_sub4=strategy_i_sub{4}; strategy_i_sub4={strategy_i_sub4.ATTRIBUTE};
154 strategy_i_sub5=strategy_i_sub{5};
155 schedparams{i} = cell2mat({strategy_i_sub5.value});
156 r=1; % we assume the strategies are identical across classes
157 switch strategy_i_sub4{r}.name
159 strategy{i} = SchedStrategy.PS;
161 strategy{i} = SchedStrategy.DPS;
163 strategy{i} = SchedStrategy.GPS;
164 case 'EPSStrategyPriority
'
165 strategy{i} = SchedStrategy.PSPRIO;
166 case 'DPSStrategyPriority
'
167 strategy{i} = SchedStrategy.DPSPRIO;
168 case 'GPSStrategyPriority
'
169 strategy{i} = SchedStrategy.GPSPRIO;
171 node{i} = Queue(model, node_name{i}, strategy{i});
172 xcapacity = {xsection_i_par{i}.value};
173 node{i}.setCapacity(xcapacity{1}); % buffer size
174 xsection_par_val{i} = {xsection_par{end}{2}.value};
175 node{i}.setNumServers(xsection_par_val{i}{1});
177 strategy_i_sub={xsection_par{i}{2}.subParameter};
178 strategy_i_sub1=strategy_i_sub{1}; strategy_i_sub1={strategy_i_sub1.subParameter};
179 csMatrix = zeros(length(strategy_i_sub1));
180 for r=1:length(strategy_i_sub1)
181 csMatrix(r,:) = cell2mat({strategy_i_sub1{r}.value});
183 node{i} = ClassSwitch(model, node_name{i}, csMatrix);
188 node{i} = Place(model, node_name{i});
190 node{i} = Transition(model, node_name{i});
195classes = {xDoc.userClass.ATTRIBUTE};
196for r=1:length(classes)
197 ref = findstring(node_name,classes{r}.referenceSource);
198 switch classes{r}.type
199 case JobClassType.toText(JobClassType.CLOSED)
200 jobclass{r} = ClosedClass(model, classes{r}.name, classes{r}.customers, node{ref}, classes{r}.priority);
201 case JobClassType.toText(JobClassType.OPEN)
202 % sink and source have been created before
203 jobclass{r} = OpenClass(model, classes{r}.name, classes{r}.priority);
204 if strcmpi(classes{r}.referenceSource,'StatelessClassSwitcher
')
205 sourceIdx = cellisa(node,'Source
');
206 node{sourceIdx}.setArrival(jobclass{r},Disabled.getInstance());
212for i=1:length(node_name)
213 xsection_i{i} = {xsection{i}};
214 xsection_i{i} = xsection_i{i}{1}; % input, service, and output sections of node i
215 xsection_javaClass{i} = {xsection_i{i}.ATTRIBUTE};
216 switch xsection_javaClass{i}{1}.className % input section
220 if xsection_i{1,i}(1).parameter(1).value == -1
221 node{i}.setCapacity(Inf);
223 node{i}.setCapacity(xsection_i{1,i}(1).parameter(1).value);
225 if isa(xsection_i{1, i}(1).parameter(2).refClass,'cell
')
226 nclasses = length(xsection_i{1, i}(1).parameter(2).refClass);
231 if xsection_i{1, i}(1).parameter(2).subParameter(c).value == -1
232 node{i}.setClassCapacity(c, Inf);
234 node{i}.setClassCapacity(c, xsection_i{1, i}(1).parameter(2).subParameter(c).value);
236 switch xsection_i{1, i}(1).parameter(3).subParameter(c).value
238 node{i}.setDropRule(c, DropStrategy.BAS);
240 node{i}.setDropRule(c, DropStrategy.DROP);
242 node{i}.setDropRule(c, DropStrategy.WAITQ);
249 nmodes = length(xsection_i{1, i}(1).parameter(1).subParameter);
251 node{i}.setModeNames(m, xsection_i{1, i}(2).parameter(1).subParameter(m).value);
255 ninputs = length(xsection_i{1, i}(1).parameter(1).subParameter(m).subParameter.subParameter);
257 refClasses = xsection_i{1, i}(1).parameter(1).subParameter(m).subParameter.subParameter(j).subParameter(2).refClass;
258 if isa(refClasses,'cell
')
259 nclasses = length(refClasses);
263 nodeName = xsection_i{1, i}(1).parameter(1).subParameter(m).subParameter.subParameter(j).subParameter(1).value;
264 targetNode = model.getNodeByName(nodeName);
266 enable = xsection_i{1, i}(1).parameter(1).subParameter(m).subParameter.subParameter(j).subParameter(2).subParameter(k).value;
268 node{i}.setEnablingConditions(m,k,targetNode,Inf);
270 node{i}.setEnablingConditions(m,k,targetNode,enable);
272 inhibit = xsection_i{1, i}(1).parameter(2).subParameter(m).subParameter.subParameter(j).subParameter(2).subParameter(k).value;
274 node{i}.setInhibitingConditions(m,k,targetNode,Inf);
276 node{i}.setInhibitingConditions(m,k,targetNode,inhibit);
283 numOfServers = xsection_i{1, i}(2).parameter(2).subParameter(m).value;
284 if numOfServers == -1
285 node{i}.setNumberOfServers(m, Inf);
287 node{i}.setNumberOfServers(m, numOfServers);
289 timingSt = xsection_i{1, i}(2).parameter(3).subParameter(m).ATTRIBUTE.classPath;
290 if strcmp(timingSt,'jmt.engine.NetStrategies.ServiceStrategies.ZeroServiceTimeStrategy
')
291 node{i}.setTimingStrategy(m,TimingStrategy.IMMEDIATE);
293 node{i}.setTimingStrategy(m,TimingStrategy.TIMED);
294 distribution = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(1).ATTRIBUTE.name;
295 lambda = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(1).value;
298 node{i}.setDistribution(m,Exp(lambda));
300 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
301 node{i}.setDistribution(m,Erlang(lambda, lambda1));
302 case 'Hyperexponential
'
303 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
304 lambda2 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(3).value;
305 node{i}.setDistribution(m,HyperExp(lambda, lambda1, lambda2));
307 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
308 lambda2 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(3).value;
309 node{i}.setDistribution(m,Coxian([lambda, lambda1], [lambda2,1]));
311 node{i}.setDistribution(m,Det(lambda));
313 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
314 node{i}.setDistribution(m,Pareto(lambda, lambda1));
316 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
317 node{i}.setDistribution(m,Gamma(lambda, lambda1));
319 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
320 node{i}.setDistribution(m,Uniform(lambda, lambda1));
322 node{i}.setDistribution(m,Replayer(lambda));
324 node{i}.setDistribution(m,Trace(lambda));
326 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
327 node{i}.setDistribution(m,Weibull(lambda1, lambda)); % scale and shape are inverted in the constructor
329 lambda1 = xsection_i{1, i}(2).parameter(3).subParameter(m).subParameter(2).subParameter(2).value;
330 node{i}.setDistribution(m,Lognormal(lambda, lambda1));
332 error('The model includes an arrival distribution not supported by the model-to-model transformation from JMT.
')
335 firingPriorities = xsection_i{1, i}(2).parameter(4).subParameter(m).value;
336 node{i}.setFiringPriorities(m, firingPriorities);
337 firingWeights = xsection_i{1, i}(2).parameter(5).subParameter(m).value;
338 node{i}.setFiringWeights(m, firingWeights);
342 if isfield(xsection_i{1, i}(3).parameter(1).subParameter(m).subParameter,'CONTENT
')
345 noutputs = length(xsection_i{1, i}(3).parameter(1).subParameter(m).subParameter.subParameter);
348 refClasses = xsection_i{1, i}(3).parameter(1).subParameter(m).subParameter.subParameter(j).subParameter(2).refClass;
349 if isa(refClasses, 'cell
')
350 nclasses = length(refClasses);
354 nodeName = xsection_i{1, i}(3).parameter(1).subParameter(m).subParameter.subParameter(j).subParameter(1).value;
356 outcome = xsection_i{1, i}(3).parameter(1).subParameter(m).subParameter.subParameter(j).subParameter(2).subParameter(k).value;
358 node{i}.setFiringOutcome(m,k,nodeName,Inf);
360 node{i}.setFiringOutcome(m,k,nodeName,outcome);
368schedparams = cell(1,length(node_name));
369% set service distributions
370for i=1:length(node_name)
371 if isa(node{i},'Source
')
372 for r=1:length(classes)
373 xsection_par{i} = {xsection{i}.parameter};
374 xsection_i_par{i} = xsection_i{i}.parameter;
375 xsection_i_subpar{i} = {xsection_i_par{i}.subParameter};
376 xarv_statdistrib{i}{r}={xsection_i_subpar{i}{1}.subParameter};
377 if isempty(xarv_statdistrib{i}{r}{r})
378 node{i}.setArrival(jobclass{r}, Disabled.getInstance());
380 xarv_statdistrib{i}{r}={xarv_statdistrib{i}{r}{r}.ATTRIBUTE};
381 xarv{i} = {xsection_i{i}(1).parameter.subParameter};
382 xarv_sec{i} = {xarv{i}{1}.subParameter};
383 switch xarv_statdistrib{i}{r}{1}.name
385 par={xarv_sec{i}{r}.subParameter}; par=par{2};
386 node{i}.setArrival(jobclass{r}, Exp(par.value));
388 par={xarv_sec{i}{r}.subParameter}; par=par{2};
389 node{i}.setArrival(jobclass{r}, Erlang(par(1).value,par(2).value));
390 case 'Hyperexponential
'
391 par={xarv_sec{i}{r}.subParameter}; par=par{2};
392 node{i}.setArrival(jobclass{r}, HyperExp(par(1).value,par(2).value,par(3).value));
394 par={xarv_sec{i}{r}.subParameter}; par=par{2};
395 node{i}.setArrival(jobclass{r}, Coxian([par(1).value,par(2).value],[par(3).value,1]));
397 par={xarv_sec{i}{r}.subParameter}; par=par{2};
398 node{i}.setArrival(jobclass{r}, Det(par.value));
400 par={xarv_sec{i}{r}.subParameter}; par=par{2};
401 node{i}.setArrival(jobclass{r}, Pareto(par(1).value, par(2).value));
403 par={xarv_sec{i}{r}.subParameter}; par=par{2};
404 node{i}.setArrival(jobclass{r}, Weibull(par(1).value, par(2).value));
406 par={xarv_sec{i}{r}.subParameter}; par=par{2};
407 node{i}.setArrival(jobclass{r}, Lognormal(par(1).value, par(2).value));
409 par={xarv_sec{i}{r}.subParameter}; par=par{2};
410 node{i}.setArrival(jobclass{r}, Gamma(par(1).value, par(2).value));
412 par={xarv_sec{i}{r}.subParameter}; par=par{2};
413 node{i}.setArrival(jobclass{r}, Uniform(par(1).value, par(2).value));
415 par={xarv_sec{i}{r}.subParameter}; par=par{2};
416 node{i}.setArrival(jobclass{r}, Replayer(par.value));
418 par={xarv_sec{i}{r}.subParameter}; par=par{2};
419 node{i}.setArrival(jobclass{r}, Trace(par.value));
421 par={xarv_sec{i}{r}.subParameter}; par=par{2};
422 node{i}.setArrival(jobclass{r}, MMPP2(par(1).value,par(2).value,par(3).value,par(4).value));
424 par={xarv_sec{i}{r}.subParameter}; par=par{2};
425 pars = {par(1).subParameter.subParameter};
428 D0 = [D0; pars{c}.value];
430 pars = {par(2).subParameter.subParameter};
433 D1 = [D1; pars{c}.value];
436 node{i}.setArrival(jobclass{r}, ax);
438 par={xarv_sec{i}{r}.subParameter}; par=par{2};
439 alpha = [par(1).subParameter.subParameter.value];
440 pars = {par(2).subParameter.subParameter};
443 T = [T; pars{c}.value];
445 if any(any(tril(T,-1))>0) % not APH
446 line_warning(mfilename,'The input model uses a general PH distribution, which
is not yet supported in LINE. Fitting the first three moments into an APH distribution.\n
');
447 PH = {T,-T*ones(size(T,1),1)*alpha};
448 ax = APH.fitCentral(map_mean(PH), map_var(PH), map_skew(PH));
452 node{i}.setArrival(jobclass{r}, ax);
454 line_error(mfilename,'The model includes an arrival distribution not supported by the model-to-model transformation from JMT.
')
455 xarv_statdistrib{i}{r}{1}.name
456 node{i}.setArrival(jobclass{r}, Exp(1)); %TODO
460 elseif isa(node{i},'Queue
') || isa(node{i},'Delay
') || isa(node{i},'DelayStation
')
461 if isempty(schedparams{i})
462 switch SchedStrategy.toId(strategy{i})
463 case {SchedStrategy.SEPT,SchedStrategy.LEPT}
464 schedparams{i} = NaN*ones(1,length(classes));
466 schedparams{i} = ones(1,length(classes));
469 for r=1:length(classes)
470 switch xsection_i_type{i}{2}.className
471 case 'StatelessClassSwitcher
'
475 xsvc_sec{i} = {xsvc{i}{1}.subParameter};
477 xsvc_sec{i} = {xsvc{i}{3}.subParameter};
479 if isempty(xsvc_sec{i}{r})
480 xsvc_statdistrib{i}{r}={struct('name
','Disabled
')};
482 xsvc_statdistrib{i}{r}={xsvc_sec{i}{r}.ATTRIBUTE};
484 para_ir = schedparams{i}(r);
485 switch xsvc_statdistrib{i}{r}{1}.name
487 node{i}.setService(jobclass{r}, Disabled.getInstance());
489 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
490 node{i}.setService(jobclass{r}, Replayer(par.value), para_ir);
492 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
493 node{i}.setService(jobclass{r}, Trace(par.value), para_ir);
495 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
496 node{i}.setService(jobclass{r}, Exp(par.value), para_ir);
498 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
499 node{i}.setService(jobclass{r}, Erlang(par(1).value,par(2).value), para_ir);
500 case 'Hyperexponential
'
501 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
502 node{i}.setService(jobclass{r}, HyperExp(par(1).value,par(2).value,par(3).value), para_ir);
504 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
505 node{i}.setService(jobclass{r}, Coxian([par(1).value,par(2).value],[par(3).value,1]), para_ir);
507 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
508 node{i}.setService(jobclass{r}, Det(par.value));
510 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
511 node{i}.setService(jobclass{r}, Pareto(par(1).value, par(2).value));
513 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
514 node{i}.setService(jobclass{r}, Weibull(par(1).value, par(2).value));
516 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
517 node{i}.setService(jobclass{r}, Lognormal(par(1).value, par(2).value));
519 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
520 node{i}.setService(jobclass{r}, Gamma(par(1).value, par(2).value));
522 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
523 node{i}.setService(jobclass{r}, MMPP2(par(1).value,par(2).value,par(3).value,par(4).value));
525 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
526 pars = {par(1).subParameter.subParameter};
529 D0 = [D0; pars{c}.value];
531 pars = {par(2).subParameter.subParameter};
534 D1 = [D1; pars{c}.value];
537 node{i}.setService(jobclass{r}, ax);
539 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
540 alpha = [par(1).subParameter.subParameter.value];
541 pars = {par(2).subParameter.subParameter};
544 T = [T; pars{c}.value];
546 if any(any(tril(T,-1))>0) % not APH
547 line_warning(mfilename,'The input model uses a general PH distribution, which
is not yet supported in LINE. Fitting the first three moments into an APH distribution.\n
');
548 PH = {T,-T*ones(size(T,1),1)*alpha};
549 ax = APH.fitCentral(map_mean(PH), map_var(PH), map_skew(PH));
553 node{i}.setService(jobclass{r}, ax);
555 par={xsvc_sec{i}{r}.subParameter}; par=par{2};
556 node{i}.setService(jobclass{r}, Uniform(par(1).value, par(2).value));
558 xsvc_statdistrib{i}{r}{1}.name
559 line_error(mfilename,'The model includes a service distribution not supported by the model-to-model transformation from JMT.
')
560 xsvc_statdistrib{i}{r}{1}.name
561 node{i}.setService(jobclass{r}, Exp(1), para_ir); %TODO
564 for c=1:length(xsection_i_par_attr{i})
565 switch xsection_i_par_attr{i}{c}.name
567 node{i}.input.setSize(xsection_i_value{i}{c}); % buffer size
574C = zeros(length(node_name)); % connection matrix
575links = {xDoc.connection.ATTRIBUTE};
577 source = findstring(orig_node_name,links{l}.source);
578 target = findstring(orig_node_name,links{l}.target);
579 % model.addLink(station{source},station{target});
580 C(source,target) = 1;
583% assign routing probabilities
584P = zeros(length(node_name)*length(classes));
585for from=1:length(node_name)
586 for target=1:length(node_name)
588 model.addLink(node{from},node{target});
593for from=1:length(node_name)
594 switch class(node{from})
599 for r=1:length(classes)
600 switch xrouting{from}{r}.name
602 node{from}.setRouting(jobclass{r},RoutingStrategy.RAND);
603 % targets = find(C(from,:));
604 % if isa(jobclass{r},'Class
')
605 % targets = setdiff(targets, [sink_idx, source_idx]);
607 % for target = targets(:)'
608 % % node{from}.setProbRouting(
jobclass{r}, node{target}, 1 / length(targets));
609 %
P((from-1)*length(
classes)+r, (target-1)*length(
classes)+r) = 1 / length(targets);
612 node{from}.setRouting(
jobclass{r},RoutingStrategy.PROB);
613 xroutprobarray = {xsection_i{from}(3).parameter.subParameter.subParameter};
614 xroutprob = {xroutprobarray{r}.subParameter}; xroutprob = xroutprob{1};
615 xroutprobdest = {xroutprob.subParameter};
616 for j=1:length(xroutprobdest)
617 xprob={xroutprobdest{j}.value};
618 target = findstring(node_name,xprob{1});
620 node{from}.setProbRouting(
jobclass{r}, node{target}, prob);
624 line_error(mfilename,
'Power of k import not supported yet.')
626 node{from}.setRouting(
jobclass{r},RoutingStrategy.RROBIN);
627 case 'Weighted Round Robin'
628 node{from}.setRouting(
jobclass{r},RoutingStrategy.WRROBIN);
629 xroutprobarray = {xsection_i{from}(3).parameter.subParameter.subParameter};
630 xroutprob = {xroutprobarray{r}.subParameter}; xroutprob = xroutprob{1};
631 xroutprobdest = {xroutprob.subParameter};
632 for j=1:length(xroutprobdest)
633 xprob={xroutprobdest{j}.value};
634 target = findstring(node_name,xprob{1});
636 node{from}.setRouting(RoutingStrategy.WRROBIN, node{target},
jobclass{r}, weight);
638 case 'Join the Shortest Queue (JSQ)'
639 node{from}.setRouting(
jobclass{r},RoutingStrategy.JSQ);
641 node{from}.setRouting(
jobclass{r},RoutingStrategy.DISABLED);
647%line_printf([
'JMT2LINE parsing time: ',num2str(Ttot),
' s\n']);
649if length(model.getIndexSourceStation)>1
650 txt = sprintf(
'LINE supports JMT models with at most a single source node. You can refactor your JMT model in several ways:\n - If you are mapping in JMT each class to a different source, this is not required. You can instead assign the same reference station to each class and configure class routing in the routing panel of the source node.\n - In more general cases, you may follow these three steps:\n (1) give a different name to each class of arrival, assigning these classes to a single source as reference station.\n (2) put a class-switch node after the source to switch the new classes into the original classes they were in the model with multiple sources.\n (3) configure the routing section of this class-switch node to set the same routing for the classes as they were in the original model.\n');
656state = zeros(length(node),length(
classes));
657if isfield(xDoc,
'preload') && ~isempty(xDoc.preload.stationPopulations)
658 npreloadStates = length(xDoc.preload.stationPopulations);
659 for st=1:npreloadStates
660 nodeName = xDoc.preload.stationPopulations(st).ATTRIBUTE.stationName;
661 ind = model.getNodeIndex(nodeName);
662 for r=1:length(xDoc.preload.stationPopulations(st).classPopulation)
663 c = model.getClassIndex(xDoc.preload.stationPopulations(st).classPopulation(r).ATTRIBUTE.refClass);
664 state(ind,c) = xDoc.preload.stationPopulations(st).classPopulation(r).ATTRIBUTE.population;
666 if isa(node{ind},
'Place')
667 %node{ind}.setState(state(ind,:));
669 line_error(mfilename,
'Import failed: Colored Petri net models are not yet supported in LINE.\n');
675 model.initFromMarginal(state);
677 line_warning(mfilename,
'Import failed to automatically initialize the model.\n');