1 | // toiderivproducer.cc
|
---|
2 | // Eric Aubourg CEA/DAPNIA/SPP septembre 1999
|
---|
3 |
|
---|
4 | #include "toiderivproducer.h"
|
---|
5 | #include "toimanager.h"
|
---|
6 | #include "archexc.h"
|
---|
7 | #include "requesthandler.h"
|
---|
8 |
|
---|
9 | set<TOI> TOIDerivProducer::reqTOIFor(TOI const&) {
|
---|
10 | set<TOI> empty;
|
---|
11 | return empty;
|
---|
12 | }
|
---|
13 |
|
---|
14 | void TOIDerivProducer::outManifest(RequestHandler* h) {
|
---|
15 | outVersion(h);
|
---|
16 | h->processOption("#COMMENT", " Producing:");
|
---|
17 | for (set<TOI>::iterator i = producedTOIs.begin(); i != producedTOIs.end(); i++) {
|
---|
18 | h->processOption("#COMMENT", " " + (*i).fullName());
|
---|
19 | set<TOI> x = reqTOIFor(*i);
|
---|
20 | if (!x.empty()) {
|
---|
21 | h->processOption("#COMMENT", " from:");
|
---|
22 | for (set<TOI>::iterator j=x.begin(); j!=x.end(); j++) {
|
---|
23 | h->processOption("#COMMENT", " " + (*j).fullName());
|
---|
24 | }
|
---|
25 | }
|
---|
26 | }
|
---|
27 | }
|
---|
28 |
|
---|
29 |
|
---|
30 | bool TOIDerivProducer::canProduce(TOI const& toi) {
|
---|
31 | // 1. Already in cache ?
|
---|
32 | map<TOI, map<TOI, TOIProducer*> >::const_iterator j = neededTOIs.find(toi);
|
---|
33 | if (j != neededTOIs.end()) return true;
|
---|
34 |
|
---|
35 | // 2. It should be in our list of possibleTOI's
|
---|
36 | TOI myTOI;
|
---|
37 | for (set<TOI>::const_iterator i = possibleTOIs.begin(); i != possibleTOIs.end(); i++) {
|
---|
38 | if ((toi.name == (*i).name) &&
|
---|
39 | (toi.index == (*i).index || (*i).index == TOI::all)) {
|
---|
40 | myTOI = (*i);
|
---|
41 | break;
|
---|
42 | }
|
---|
43 | }
|
---|
44 | if (myTOI.name == "") return false; // not in list
|
---|
45 |
|
---|
46 | // 3. Handle options
|
---|
47 |
|
---|
48 | set<string> extraopts = toi.options;
|
---|
49 |
|
---|
50 | // 3a should contain mandatory options
|
---|
51 | for (set<string>::iterator i = myTOI.reqOptions.begin();
|
---|
52 | i != myTOI.reqOptions.end(); i++) {
|
---|
53 | if (extraopts.find(*i) == extraopts.end()) return false;
|
---|
54 | }
|
---|
55 |
|
---|
56 | // 3b remove local options
|
---|
57 |
|
---|
58 | for (set<string>::iterator i = myTOI.options.begin();
|
---|
59 | i != myTOI.options.end(); i++) {
|
---|
60 | extraopts.erase(*i);
|
---|
61 | }
|
---|
62 |
|
---|
63 | // 4. Find producers, distribute remaining options
|
---|
64 | map<TOI, TOIProducer*> fullInputTOI;
|
---|
65 | set<TOI> inputTOIs = reqTOIFor(toi);
|
---|
66 | for (set<TOI>::iterator i = inputTOIs.begin(); i != inputTOIs.end(); i++) {
|
---|
67 | TOI inTOI = *i;
|
---|
68 | TOIProducer* prod = TOIManager::findTOIProducer(inTOI);
|
---|
69 | if (!prod) return false;
|
---|
70 | if (!extraopts.empty()) {
|
---|
71 | set<string> xopts = prod->getAvailOptions(inTOI);
|
---|
72 | for (set<string>::iterator j = xopts.begin(); j != xopts.end(); j++) {
|
---|
73 | if (extraopts.find(*j) != extraopts.end()) {
|
---|
74 | inTOI.options.insert(*j);
|
---|
75 | extraopts.erase(*j);
|
---|
76 | }
|
---|
77 | }
|
---|
78 | }
|
---|
79 | fullInputTOI[inTOI] = prod;
|
---|
80 | }
|
---|
81 |
|
---|
82 | if (!extraopts.empty()) return false;
|
---|
83 |
|
---|
84 | neededTOIs[toi] = fullInputTOI;
|
---|
85 | return true;
|
---|
86 | }
|
---|
87 |
|
---|
88 | set<string> TOIDerivProducer::getAvailOptions(TOI const& toi) {
|
---|
89 | // toi.options.clear();
|
---|
90 | // toi.index = -2;
|
---|
91 | // if (!canProduce(toi)) throw ArchExc("cannot produce " + toi.name);
|
---|
92 | set<string> s = getProperAvailOptions(toi);
|
---|
93 | map<TOI, TOIProducer*> need = neededTOIs[toi];
|
---|
94 | for (map<TOI, TOIProducer*>::iterator i = need.begin(); i != need.end(); i++) {
|
---|
95 | set<string> s1 = (*i).second->getAvailOptions((*i).first);
|
---|
96 | s.insert(s1.begin(), s1.end());
|
---|
97 | }
|
---|
98 | return s;
|
---|
99 | }
|
---|
100 |
|
---|
101 | void TOIDerivProducer::addTOI(TOI& toi, TOIAbsorber* client) {
|
---|
102 | TOIProducer::addTOI(toi, client);
|
---|
103 | map<TOI, TOIProducer*> m = neededTOIs[toi];
|
---|
104 | for (map<TOI, TOIProducer*>::iterator i = m.begin(); i != m.end(); i++) {
|
---|
105 | TOI toi2 = (*i).first;
|
---|
106 | (*i).second->addTOI(toi2,this);
|
---|
107 | }
|
---|
108 | }
|
---|
109 |
|
---|
110 | long TOIDerivProducer::wontNeedEarlier(TOI const& toi, TOIAbsorber* client, long t) {
|
---|
111 | long xt = TOIProducer::wontNeedEarlier(toi, client, t);
|
---|
112 | if (xt>0) propagateLowBound(toi, xt);
|
---|
113 | return xt;
|
---|
114 | }
|
---|
115 |
|
---|
116 | // if no need for past values...
|
---|
117 | void TOIDerivProducer::propagateLowBound(TOI const& toi, long sampleNum) {
|
---|
118 | CHKPROD
|
---|
119 | map<TOI, TOIProducer*> need = neededTOIs[toi];
|
---|
120 | for (map<TOI, TOIProducer*>::iterator i = need.begin(); i != need.end(); i++) {
|
---|
121 | (*i).second->wontNeedEarlier((*i).first, this, sampleNum);
|
---|
122 | }
|
---|
123 | }
|
---|