View Javadoc

1   /***
2    * Cecilia ADL Compiler
3    * Copyright (C) 2006-2008 STMicroelectronics
4    *
5    * This library is free software; you can redistribute it and/or
6    * modify it under the terms of the GNU Lesser General Public
7    * License as published by the Free Software Foundation; either
8    * version 2 of the License, or (at your option) any later version.
9    *
10   * This library is distributed in the hope that it will be useful,
11   * but WITHOUT ANY WARRANTY; without even the implied warranty of
12   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13   * Lesser General Public License for more details.
14   *
15   * You should have received a copy of the GNU Lesser General Public
16   * License along with this library; if not, write to the Free Software
17   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18   *
19   * Contact: fractal@objectweb.org
20   *
21   * Author: Matthieu Leclercq
22   */
23  
24  package org.objectweb.fractal.cecilia.adl;
25  
26  import java.util.ArrayList;
27  import java.util.Map;
28  import java.util.logging.Level;
29  
30  import org.objectweb.fractal.adl.ADLErrors;
31  import org.objectweb.fractal.adl.ADLException;
32  import org.objectweb.fractal.adl.Compiler;
33  import org.objectweb.fractal.adl.CompilerError;
34  import org.objectweb.fractal.adl.ComponentVisitor;
35  import org.objectweb.fractal.adl.Definition;
36  import org.objectweb.fractal.adl.DefinitionVisitor;
37  import org.objectweb.fractal.adl.Factory;
38  import org.objectweb.fractal.adl.Loader;
39  import org.objectweb.fractal.adl.Node;
40  import org.objectweb.fractal.adl.error.GenericErrors;
41  import org.objectweb.fractal.adl.util.FractalADLLogManager;
42  import org.objectweb.fractal.api.Component;
43  import org.objectweb.fractal.api.NoSuchInterfaceException;
44  import org.objectweb.fractal.api.control.BindingController;
45  import org.objectweb.fractal.api.control.IllegalBindingException;
46  import org.objectweb.fractal.api.control.IllegalLifeCycleException;
47  import org.objectweb.fractal.cecilia.adl.file.FileCollectionProvider;
48  import org.objectweb.fractal.cecilia.adl.file.FileProvider;
49  import org.objectweb.fractal.task.core.Record;
50  import org.objectweb.fractal.task.core.TaskException;
51  import org.objectweb.fractal.task.core.TaskInterface;
52  import org.objectweb.fractal.task.core.control.TaskExecutionException;
53  
54  /**
55   * Implementation of the {@link Factory} interface.
56   * 
57   * @see org.objectweb.fractal.adl.BasicFactory
58   */
59  public class CeciliaFactory implements Factory, BindingController {
60  
61    // --------------------------------------------------------------------------
62    // Client interfaces
63    // --------------------------------------------------------------------------
64  
65    /** The name of the {@link Loader} client interface of this component. */
66    public static final String LOADER_ITF_NAME  = "loader";
67  
68    /** The name of the {@link Compiler} client interface of this component. */
69    public static final String VISITOR_ITF_NAME = "visitor";
70  
71    /** The {@link Loader} used by this factory. */
72    private Loader             loaderItf;
73  
74    /** The {@link ComponentVisitor} used by this factory. */
75    private DefinitionVisitor  visitorItf;
76  
77    // --------------------------------------------------------------------------
78    // Implementation of the Factory interface
79    // --------------------------------------------------------------------------
80  
81    // Suppress unchecked warning to avoid to change Factory interface
82    @SuppressWarnings("unchecked")
83    public Object newComponentType(final String name, final Map context)
84        throws ADLException {
85      throw new UnsupportedOperationException();
86    }
87  
88    // Suppress unchecked warning to avoid to change Factory interface
89    @SuppressWarnings("unchecked")
90    public Object newComponent(final String name, final Map context)
91        throws ADLException {
92  
93      if (FractalADLLogManager.STEP.isLoggable(Level.FINE))
94        FractalADLLogManager.STEP.fine("[basic-factory] Load ADL \'" + name
95            + "\'");
96  
97      // Try loading this definition.
98      final Definition d = loaderItf.load(name, context);
99  
100     // Do we have to stop when we're done checking the ADL ?
101     final Object checkADL = context.get("check-adl");
102     if (checkADL != null && ((Boolean) checkADL)) {
103       FractalADLLogManager.STEP.info("[basic-factory] ADL \'" + name
104           + "\' loaded successfully, it looks correct");
105       return d;
106     }
107 
108     // No, we don't.
109     FractalADLLogManager.STEP
110         .fine("[basic-factory] ADL loaded successfully, build task graph");
111 
112     Component taskGraph;
113     try {
114       taskGraph = visitorItf.visit(new ArrayList<Node>(), d, context);
115     } catch (final TaskException e1) {
116       throw new CompilerError(GenericErrors.INTERNAL_ERROR, e1,
117           "Task component instantiation problem during the creation of the task graph.");
118     }
119 
120     FractalADLLogManager.STEP
121         .fine("[basic-factory] Task graph built successfully, execute tasks");
122 
123     Object result = null;
124     try {
125       final Record outputRecord = new Record("role:outputFiles, id:%", d);
126       for (final Object taskItf : taskGraph.getFcInterfaces()) {
127         if (outputRecord.equals(((TaskInterface) taskItf).getFcRecord())) {
128           if (taskItf instanceof FileProvider)
129             result = ((FileProvider) taskItf).getFile();
130           if (taskItf instanceof FileCollectionProvider)
131             result = ((FileCollectionProvider) taskItf).getFiles();
132         }
133       }
134     } catch (final TaskExecutionException e) {
135       if (e.getCause() instanceof ADLException)
136         throw (ADLException) e.getCause();
137       else
138         throw new ADLException(ADLErrors.TASK_EXECUTION_ERROR, e.getCause());
139     } catch (final Exception e) {
140       throw new ADLException(ADLErrors.TASK_EXECUTION_ERROR, e);
141     }
142 
143     FractalADLLogManager.STEP
144         .fine("[basic-factory] Tasks executed successfully.");
145     return result;
146   }
147 
148   public void bindFc(final String itfName, final Object value)
149       throws NoSuchInterfaceException, IllegalBindingException,
150       IllegalLifeCycleException {
151 
152     if (itfName == null) {
153       throw new IllegalArgumentException("Interface name can't be null");
154     }
155 
156     // XXX check whether it is null or not !!
157 
158     try {
159       if (itfName.equals(LOADER_ITF_NAME)) {
160         this.loaderItf = (Loader) value;
161       } else if (itfName.equals(VISITOR_ITF_NAME)) {
162         this.visitorItf = (DefinitionVisitor) value;
163       } else {
164         throw new NoSuchInterfaceException(
165             "Unable to find the interface named '" + itfName + "'");
166       }
167     } catch (final ClassCastException cce) {
168       cce.printStackTrace();
169       throw new IllegalBindingException("Unmatching interface types");
170     }
171   }
172 
173   public String[] listFc() {
174     return new String[]{LOADER_ITF_NAME, VISITOR_ITF_NAME};
175   }
176 
177   public Object lookupFc(final String itfName) throws NoSuchInterfaceException {
178 
179     if (itfName == null) {
180       throw new IllegalArgumentException("Interface name can't be null");
181     }
182 
183     if (itfName.equals(LOADER_ITF_NAME)) {
184       return this.loaderItf;
185     } else if (itfName.equals(VISITOR_ITF_NAME)) {
186       return this.visitorItf;
187     } else {
188       throw new NoSuchInterfaceException("Unable to find the interface named '"
189           + itfName + "'");
190     }
191   }
192 
193   public void unbindFc(final String itfName) throws NoSuchInterfaceException,
194       IllegalBindingException, IllegalLifeCycleException {
195 
196     if (itfName == null) {
197       throw new IllegalArgumentException("Interface name can't be null");
198     }
199 
200     if (itfName.equals(LOADER_ITF_NAME)) {
201       this.loaderItf = null;
202     } else if (itfName.equals(VISITOR_ITF_NAME)) {
203       this.visitorItf = null;
204     } else {
205       throw new NoSuchInterfaceException("Unable to find the interface named '"
206           + itfName + "'");
207     }
208 
209   }
210 }