degate 0.1.1
Layer.h
Go to the documentation of this file.
00001 /* -*-c++-*-
00002 
00003   This file is part of the IC reverse engineering tool degate.
00004 
00005   Copyright 2008, 2009, 2010 by Martin Schobert
00006 
00007   Degate is free software: you can redistribute it and/or modify
00008   it under the terms of the GNU General Public License as published by
00009   the Free Software Foundation, either version 3 of the License, or
00010   any later version.
00011 
00012   Degate is distributed in the hope that it will be useful,
00013   but WITHOUT ANY WARRANTY; without even the implied warranty of
00014   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015   GNU General Public License for more details.
00016 
00017   You should have received a copy of the GNU General Public License
00018   along with degate. If not, see <http://www.gnu.org/licenses/>.
00019 
00020 */
00021 
00022 #ifndef __LAYER_H__
00023 #define __LAYER_H__
00024 
00025 #include "globals.h"
00026 
00027 #include "Rectangle.h"
00028 #include "QuadTree.h"
00029 #include "PlacedLogicModelObject.h"
00030 
00031 #include "Image.h"
00032 #include "ScalingManager.h"
00033 
00034 #include <set>
00035 #include <stdexcept>
00036 
00037 namespace degate {
00038 
00039   /**
00040    * Representation of a chip layer.
00041    */
00042   class Layer {
00043 
00044     friend class LogicModel;
00045 
00046   public:
00047 
00048     /**
00049      * Enums to declare the type of a layer.
00050      */
00051 
00052     enum LAYER_TYPE {
00053       UNDEFINED = 0,
00054       METAL = 1,
00055       LOGIC = 2,
00056       TRANSISTOR = 3
00057     };
00058 
00059     typedef std::tr1::shared_ptr<PlacedLogicModelObject> quadtree_element_type;
00060 
00061     typedef region_iterator<quadtree_element_type> qt_region_iterator;
00062     typedef qt_region_iterator object_iterator;
00063 
00064   private:
00065 
00066     QuadTree<quadtree_element_type> quadtree;
00067 
00068     LAYER_TYPE layer_type;
00069 
00070     layer_position_t layer_pos;
00071 
00072     std::tr1::shared_ptr<ScalingManager<BackgroundImage> > scaling_manager;
00073 
00074     // store shared pointers to objects, that belong to the layer
00075     typedef std::map<object_id_t, PlacedLogicModelObject_shptr> object_collection;
00076     object_collection objects;
00077 
00078     bool enabled;
00079     std::string description;
00080 
00081     layer_id_t layer_id;
00082 
00083   protected:
00084 
00085     /**
00086      * Add an logic model object into this layer.
00087      * @throw DegateRuntimeException Is thrown if the object
00088      *   cannot be inserted into the quadtree.
00089      * @throw DegateLogicException
00090      */
00091 
00092     void add_object(std::tr1::shared_ptr<PlacedLogicModelObject> o);
00093 
00094 
00095     /**
00096      * Remove object from layer.
00097      * @throw DegateRuntimeException Is thrown if the object
00098      *   cannot be removed from the quadtree.
00099      */
00100 
00101     void remove_object(std::tr1::shared_ptr<PlacedLogicModelObject> o);
00102 
00103   public:
00104 
00105 
00106     /**
00107      * Create a new logic model layer.
00108      */
00109 
00110     Layer(BoundingBox const & bbox, LAYER_TYPE _layer_type = Layer::UNDEFINED);
00111 
00112     /**
00113      * Create a new logic model layer.
00114      */
00115 
00116     Layer(BoundingBox const & bbox, LAYER_TYPE _layer_type,
00117           BackgroundImage_shptr img);
00118 
00119     /**
00120      * Destruct a layer.
00121      */
00122 
00123     virtual ~Layer();
00124 
00125     /**
00126      * Get the width of a layer.
00127      */
00128 
00129     unsigned int get_width() const;
00130 
00131     /**
00132      * Get the height of a layer.
00133      */
00134 
00135     unsigned int get_height() const;
00136 
00137     /**
00138      * Get the bounding box for a layer.
00139      */
00140     BoundingBox const& get_bounding_box() const;
00141 
00142     /**
00143      * Get layer type of this layer as human readable string, e.g. the string
00144      * "metal" for a layer of type Layer::METAL .
00145      */
00146 
00147     const std::string get_layer_type_as_string() const;
00148 
00149     /**
00150      * Get a layer type type as human readable string.
00151      */
00152     static const std::string get_layer_type_as_string(LAYER_TYPE _layer_type);
00153 
00154     /**
00155      * Parse a layer type indicating string.
00156      * @exception DegateRuntimeException This exception is thrown if the string
00157      *   cannot be parsed.
00158      */
00159     static LAYER_TYPE get_layer_type_from_string(std::string const& layer_type_str);
00160 
00161 
00162     /**
00163      * Get layer type.
00164      */
00165 
00166     LAYER_TYPE get_layer_type() const;
00167 
00168     /**
00169      * Set layer type.
00170      */
00171 
00172     void set_layer_type(LAYER_TYPE _layer_type);
00173 
00174 
00175     /**
00176      * Check if a layer has logic model objects or not.
00177      */
00178 
00179     bool is_empty() const;
00180 
00181 
00182     /**
00183      * Get the position of the layer within the layer stack.
00184      */
00185 
00186     layer_position_t get_layer_pos() const;
00187 
00188 
00189     /**
00190      * Get an iterator to iterate over all placed objects.
00191      */
00192 
00193     object_iterator objects_begin();
00194 
00195     /**
00196      * Get an end iterator.
00197      */
00198 
00199     object_iterator objects_end();
00200 
00201     /**
00202      * Get an iterator to iterate over a region.
00203      */
00204 
00205     qt_region_iterator region_begin(int min_x, int max_x, int min_y, int max_y);
00206 
00207     /**
00208      * Get an iterator to iterate over a region.
00209      */
00210 
00211     qt_region_iterator region_begin(BoundingBox const & bbox);
00212 
00213     /**
00214      * Get an end marker for region iteration.
00215      */
00216 
00217     qt_region_iterator region_end();
00218 
00219 
00220     /**
00221      * Set the background image for a layer.
00222      * Calling this method will also initialize the ScalingManager, that
00223      * handles multiple prescaled versions of the background image.
00224      * The ScalingManager will write the prescaled images into subdirectories
00225      * of the the background image.
00226      */
00227 
00228     void set_image(BackgroundImage_shptr img);
00229 
00230 
00231     /**
00232      * Get the background image.
00233      * @return Returns a shared pointer to the background image.
00234      * @exception DegateLogicException If you did not set the background image, then this
00235      *   exception is thrown.
00236      * @see set_image()
00237      */
00238 
00239     BackgroundImage_shptr get_image();
00240 
00241     /**
00242      * Get the directory name for the image, that represents the
00243      * background image of the layer.
00244      * @exception DegateLogicException If you did not set the background image, then this
00245      *   exception is thrown.
00246      */
00247 
00248     std::string get_image_filename() const;
00249 
00250     /**
00251      * Check if the layer has a background image.
00252      */
00253 
00254     bool has_background_image() const;
00255 
00256 
00257     /**
00258      * Unset the background image.
00259      * This will destroy the image and it's scaling manager object and it will remove
00260      * the data from the project dir.
00261      * @exception DegateLogicException This excpetion is thrown if there is no background image.
00262      */
00263 
00264     void unset_image();
00265 
00266     /**
00267      * Get the scaling manager.
00268      * If you want to access the background image of a layer, that is the
00269      * chip surface depicting image, you have to ask for the ScalingMananger.
00270      * From the scaling mananger you will get the image.
00271      * @return Returns a shared pointer to the  scaling manager object.
00272      *   The pointer can be a NULL pointer. This is the case if you did not
00273      *   initialized it via set_image()
00274      * @see set_image()
00275      */
00276 
00277     ScalingManager_shptr get_scaling_manager();
00278 
00279     /**
00280      * Print the layer.
00281      */
00282     void print(std::ostream & os = std::cout);
00283 
00284     /**
00285      * Notify the layer that a shape of a logic model object changed.
00286      * This will adjust the quadtree.
00287      * @exception CollectionLookupException This exception is thrown if
00288      *    thetre is no object in the layer, that has this object ID.
00289      * @exception InvalidObjectIDException Is raised, if \p object_id
00290      *    has an invalid ID.
00291      */
00292 
00293     void notify_shape_change(object_id_t object_id);
00294 
00295     /**
00296      * Get an object at a specific position.
00297      * If multiple objects are placed at coordinate \p x, \p y, then the first
00298      * one is returned. But if there is a gate port, the port is returned.
00299      * @param x The x-position.
00300      * @param y The y-position.
00301      * @param max_distance It is possible to check for objects, which are
00302      *   not directly placed in a way, that \p x and \p y are within the shape
00303      *   of an object. Therefore the parameter \p max_distance specifies an
00304      *   allowed distance to the object.
00305      * @return If there is an object at the position, a shared pointer to
00306      *   it is returned. If there is no object, then a NULL pointer representation
00307      *   is returned.
00308      */
00309 
00310     PlacedLogicModelObject_shptr get_object_at_position(int x, int y, int max_distance = 0);
00311 
00312     /**
00313      * Check for placed objects in a region of type given by template param.
00314      * @return Returns true, if there is a an object of the specified type in the region.
00315      *   Else it returns false.
00316      */
00317 
00318     template<typename LogicModelObjectType>
00319     bool exists_type_in_region(unsigned int min_x, unsigned int max_x,
00320                                unsigned int min_y, unsigned int max_y) {
00321       for(Layer::qt_region_iterator iter = quadtree.region_iter_begin(min_x, max_x, min_y, max_y);
00322           iter != quadtree.region_iter_end(); ++iter) {
00323         
00324         if(std::tr1::dynamic_pointer_cast<LogicModelObjectType>(*iter) != NULL) {
00325           return true;
00326         }
00327       }
00328       return false;      
00329     }
00330 
00331 
00332     /**
00333      * Check for placed gates in a region and return the distance to
00334      * the boundary.
00335      * @return Returns the distance from \p x to the right boundary or
00336      *   from \p y to the bottom boundary depending on \p query_horizontal_distance.
00337      *   If there is no gate, this method returns 0.
00338      */
00339 
00340     unsigned int get_distance_to_gate_boundary(unsigned int x, unsigned int y,
00341                                                bool query_horizontal_distance = true,
00342                                                unsigned int width = 0,
00343                                                unsigned int height = 0);
00344 
00345 
00346     /**
00347      * Enable a layer.
00348      */
00349 
00350     void set_enabled(bool state = true);
00351 
00352     /**
00353      * Check if a layer is enabled.
00354      * Enabled means, that the layer is visible to the user.
00355      */
00356 
00357     bool is_enabled() const;
00358 
00359 
00360     /**
00361      * Get layer description.
00362      */
00363 
00364     std::string get_description() const;
00365 
00366 
00367     /**
00368      * Set layer description.
00369      */
00370 
00371     void set_description(std::string const& description);
00372 
00373 
00374     /**
00375      * Set layer position.
00376      */
00377     void set_layer_pos(layer_position_t pos) { layer_pos = pos; }
00378 
00379     /**
00380      * Set the layer ID. The layer ID is not an object ID. The only requirement is
00381      * that each layer has a unique and position-independend ID.
00382      */
00383 
00384     virtual void set_layer_id(layer_id_t lid) { layer_id = lid; }
00385 
00386     /**
00387      * Get the layer ID.
00388      */
00389 
00390     virtual layer_id_t get_layer_id() const { return layer_id; }
00391 
00392     /**
00393      * Check if the layer has a valid layer ID.
00394      */
00395 
00396     virtual bool has_valid_layer_id() const { return layer_id != 0; }
00397 
00398   };
00399 
00400 }
00401 
00402 #endif