mirror of https://github.com/KLayout/klayout.git
Merge branch 'pymod' into net-extract
This commit is contained in:
commit
c75e67268b
72
README.md
72
README.md
|
|
@ -9,9 +9,20 @@ For more details see http://www.klayout.org.
|
|||
|
||||
## Building requirements
|
||||
|
||||
Building on Linux:
|
||||
|
||||
* Qt 4.7 or later (4.6 with some restrictions) or Qt 5
|
||||
* gcc 4.6 or later or clang 3.8 or later
|
||||
|
||||
Building on Windows with MSYS2:
|
||||
|
||||
* MSYS2 with gcc, Qt4 or 5, zlib, ruby and python packages installed
|
||||
|
||||
Building on Windows with MSVC 2017:
|
||||
|
||||
* MSVC 2017
|
||||
* Build requisites from klayout-kit
|
||||
|
||||
For more build instructions see http://www.klayout.de/build.html.
|
||||
|
||||
## Build options
|
||||
|
|
@ -25,16 +36,16 @@ For more build instructions see http://www.klayout.de/build.html.
|
|||
|
||||
### Plain building for Qt4
|
||||
|
||||
./build.sh
|
||||
|
||||
./build.sh
|
||||
|
||||
### Plain building for Qt5
|
||||
|
||||
./build.sh -qt5
|
||||
|
||||
./build.sh -qt5
|
||||
|
||||
### Building without Qt binding
|
||||
|
||||
./build.sh -without-qtbinding
|
||||
|
||||
|
||||
### Debug build
|
||||
|
||||
./build.sh -debug
|
||||
|
|
@ -63,8 +74,8 @@ For more build instructions see http://www.klayout.de/build.html.
|
|||
|
||||
### Pass make options
|
||||
|
||||
./build.sh -j4
|
||||
|
||||
./build.sh -j4
|
||||
|
||||
(for running 4 jobs in parallel)
|
||||
|
||||
### More options
|
||||
|
|
@ -80,9 +91,54 @@ Go to the build directory (i.e. "bin-release") and enter
|
|||
export TESTTMP=testtmp # path to a directory that will hold temporary data (will be created)
|
||||
export TESTSRC=.. # path to the source directory
|
||||
./ut_runner
|
||||
|
||||
|
||||
For more options use
|
||||
|
||||
./ut_runner -h
|
||||
|
||||
## Build instructions (Windows, MSYS2)
|
||||
|
||||
From the MSYS2 MinGW bash (32 bit or 64 bit) use the same commands as for Linux to build the
|
||||
binaries.
|
||||
|
||||
## Build instructions (Windows, MSVC 2017)
|
||||
|
||||
The combination supported and tested was Qt 5.11/MSVC 2017 64bit.
|
||||
It's sufficient to install the build tools from MSVC's community edition.
|
||||
|
||||
A build script similar to build.sh is provided for Windows
|
||||
(build.bat).
|
||||
|
||||
For details about this build script use
|
||||
|
||||
```
|
||||
build.bat -h
|
||||
```
|
||||
|
||||
For MSVC builds a number of third party libraries are required:
|
||||
|
||||
* Ruby
|
||||
* Python
|
||||
* zlib
|
||||
* expat
|
||||
* curl
|
||||
* pthread-win
|
||||
|
||||
The "klayout-bits4msvc2017" project (https://github.com/klayoutmatthias/klayout_bits4msvc2017) targets towards providing a binary distribution for this purpose.
|
||||
See the release notes there for download links. Download the .zip archive from there and unpack it to some folder, e.g. "c:\klayout-bits".
|
||||
|
||||
The build script needs the path to this package. "qmake" and (for obtaining the build version) "git" should be in the path. If qmake is not in the path, you can use "build.bat -qmake ..." to specify qmake's path.
|
||||
|
||||
Here is an example for the build.bat call:
|
||||
|
||||
```
|
||||
build.bat -bits c:\klayout-bits
|
||||
```
|
||||
|
||||
The 3rd party bits kit can also be used to build the Python
|
||||
standalone package on setuptools. Specify the full path to the 3rd party package up to the compiler and architecture. On 64bit with the bits package installed in "c:\klayout-bits" the build call is this:
|
||||
|
||||
```
|
||||
set KLAYOUT_BITS=c:\klayout-bits\msvc2017\x64
|
||||
python setup.py build
|
||||
```
|
||||
|
|
|
|||
|
|
@ -0,0 +1,255 @@
|
|||
|
||||
@echo off
|
||||
setlocal EnableDelayedExpansion
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem KLAYOUT build script
|
||||
rem See build.bat -h for details
|
||||
rem
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem parse command lines
|
||||
|
||||
set CONFIG=release
|
||||
set HAVE_QTBINDINGS=1
|
||||
set HAVE_QT=1
|
||||
set HAVE_64BIT_COORD=0
|
||||
set HAVE_PYTHON=1
|
||||
set HAVE_RUBY=1
|
||||
set MAKE_OPT=
|
||||
|
||||
set arch=x64
|
||||
set compiler=msvc2017
|
||||
set dry_run=0
|
||||
set option-qmake=qmake
|
||||
set "option-bits=c:\klayout-bits"
|
||||
set "option-build=%TEMP%\klayout-build"
|
||||
set "option-bin=%TEMP%\klayout-bin"
|
||||
|
||||
set "option="
|
||||
for %%a in (%*) do (
|
||||
if not defined option (
|
||||
set arg=%%a
|
||||
if "!arg:~0,1!" equ "-" (
|
||||
if "!arg!" equ "-h" (
|
||||
set "option-h=1"
|
||||
set "option="
|
||||
) else if "!arg!" equ "--help" (
|
||||
set "option-h=1"
|
||||
set "option="
|
||||
) else if "!arg!" equ "-help" (
|
||||
set "option-h=1"
|
||||
set "option="
|
||||
) else if "!arg!" equ "-bits" (
|
||||
set "option=!arg!"
|
||||
) else if "!arg!" equ "-qmake" (
|
||||
set "option=!arg!"
|
||||
) else if "!arg!" equ "-build" (
|
||||
set "option=!arg!"
|
||||
) else if "!arg!" equ "-bin" (
|
||||
set "option-bin=%TEMP%\klayout-bin"
|
||||
set "option=!arg!"
|
||||
) else if "!arg!" equ "-prefix" (
|
||||
set "option-bin=%TEMP%\klayout-bin"
|
||||
set "option=!arg!"
|
||||
) else if "!arg!" equ "-build" (
|
||||
set "option=!arg!"
|
||||
) else if "!arg!" equ "-debug" (
|
||||
set "CONFIG=debug"
|
||||
) else if "!arg!" equ "-release" (
|
||||
set "CONFIG=release"
|
||||
) else if "!arg!" equ "-with-qtbinding" (
|
||||
set "HAVE_QTBINDINGS=1"
|
||||
) else if "!arg!" equ "-without-qtbinding" (
|
||||
set "HAVE_QTBINDINGS=0"
|
||||
) else if "!arg!" equ "-without-qt" (
|
||||
set "HAVE_QT=0"
|
||||
) else if "!arg!" equ "-with-64bit-coord" (
|
||||
set "HAVE_64BIT_COORD=1"
|
||||
) else if "!arg!" equ "-without-64bit-coord" (
|
||||
set "HAVE_64BIT_COORD=0"
|
||||
) else if "!arg!" equ "-nopython" (
|
||||
set "HAVE_PYTHON=0"
|
||||
) else if "!arg!" equ "-noruby" (
|
||||
set "HAVE_RUBY=0"
|
||||
) else if "!arg!" equ "-dry-run" (
|
||||
set "dry_run=1"
|
||||
) else if "!arg!" equ "-x64" (
|
||||
set "arch=x64"
|
||||
) else if "!arg!" equ "-x86" (
|
||||
set "arch=x86"
|
||||
)
|
||||
) else (
|
||||
set "MAKE_OPT=!MAKE_OPT! !arg!"
|
||||
)
|
||||
) else (
|
||||
set "option!option!=%%a"
|
||||
set "option="
|
||||
)
|
||||
)
|
||||
|
||||
if defined option-h (
|
||||
echo build.bat - KLayout build script
|
||||
echo.
|
||||
echo Mandatory options:
|
||||
echo -bits [path] Path to the 3rd party binary kit
|
||||
echo -build [path] Path to the build directory
|
||||
echo -bin [path] Path to the installation directory
|
||||
echo -prefix [path] Same as -bin
|
||||
echo -x86 32 bit build
|
||||
echo -x64 64 bit build [default]
|
||||
echo.
|
||||
echo Other options:
|
||||
echo -h -help --help Show this help
|
||||
echo -qmake [path] Path to the qmake binary
|
||||
echo -debug Perform a debug build
|
||||
echo -release Perform a release build [the default]
|
||||
echo -with-qtbinding Enable Qt support for Ruby/Python [the default]
|
||||
echo -without-qtbinding Disable Qt support for Ruby/Python
|
||||
echo -without-qt Entirely Qt-free build of a tool subset
|
||||
echo -with-64bit-coord Enable 64bit coordinate support [experimental]
|
||||
echo -without-64bit-coord Disable 64bit coordinate support [default]
|
||||
echo -nopython Dont include Python support
|
||||
echo -noruby Dont include Ruby support
|
||||
echo -dry-run Dont actually make
|
||||
goto :eof
|
||||
)
|
||||
|
||||
echo Analysing installation ...
|
||||
echo.
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem locate MSVC 2017 on the system
|
||||
|
||||
set MSVC2017_COMPILER_INST=notfound
|
||||
rem VS 2017 sets exactly one install as the "main" install, so we may find MSBuild in there.
|
||||
reg query "HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\VisualStudio\SxS\VS7" /v 15.0 /reg:32 >nul 2>nul
|
||||
if NOT ERRORLEVEL 1 (
|
||||
for /F "tokens=1,2*" %%i in ('reg query "HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\VisualStudio\SxS\VS7" /v 15.0 /reg:32') DO (
|
||||
if "%%i"=="15.0" (
|
||||
if exist "%%k\VC\Auxiliary\Build" (
|
||||
set "MSVC2017_COMPILER_INST=%%k\VC\Auxiliary\Build"
|
||||
set "msg=Found MSVC installation at !MSVC2017_COMPILER_INST!"
|
||||
echo !msg!
|
||||
)
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
if "%MSVC2017_COMPILER_INST%" == "notfound" (
|
||||
echo ERROR: Unable to find MSVC 2017 installation
|
||||
goto :eof
|
||||
)
|
||||
if %arch% equ x64 (
|
||||
call "%MSVC2017_COMPILER_INST%\vcvars64"
|
||||
) else (
|
||||
call "%MSVC2017_COMPILER_INST%\vcvars32"
|
||||
)
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem check the kit
|
||||
|
||||
if not exist "%option-bits%"\%compiler%\%arch% (
|
||||
echo ERROR: no 3rd party binary kit found in %option-bits%\%compiler%\%arch%
|
||||
goto :eof
|
||||
)
|
||||
if not exist "%option-bits%\%compiler%\%arch%\ruby\bin\ruby.exe" (
|
||||
echo ERROR: %option-bits% not installed properly or
|
||||
echo path does not point to architecture folder.
|
||||
echo Use -bits to specfiy the path to the 3rd party binary kit.
|
||||
goto :eof
|
||||
)
|
||||
echo Using bits from %option-bits%\%compiler%\%arch%
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem check the qmake binary
|
||||
|
||||
"%option-qmake%" -v >nul 2>nul
|
||||
if ERRORLEVEL 1 (
|
||||
echo ERROR: Not a valid qmake: %option-qmake%
|
||||
echo Use -qmake option to specify the path to the qmake binary.
|
||||
goto :eof
|
||||
)
|
||||
echo Using qmake from %option-qmake%
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem read klayout Version
|
||||
|
||||
for /F "tokens=1" %%i in ('type version.sh') do (
|
||||
set line=%%i
|
||||
if "!line:~0,16!" equ "KLAYOUT_VERSION=" (
|
||||
set "version=!line:~16,100!"
|
||||
set "KLAYOUT_VERSION=!version:"=!"
|
||||
)
|
||||
)
|
||||
|
||||
date /t >%TEMP%\klayout-build-tmp.txt
|
||||
set /P KLAYOUT_VERSION_DATE=<%TEMP%\klayout-build-tmp.txt
|
||||
del %TEMP%\klayout-build-tmp.txt
|
||||
|
||||
rem The short SHA hash of the commit
|
||||
git rev-parse --short HEAD 2>nul >%TEMP%\klayout-build-tmp.txt
|
||||
set /P KLAYOUT_VERSION_REV=<%TEMP%\klayout-build-tmp.txt
|
||||
if ERRORLEVEL 1 (
|
||||
set "KLAYOUT_VERSION_REV=LatestSourcePackage"
|
||||
)
|
||||
del %TEMP%\klayout-build-tmp.txt
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem dump settings
|
||||
|
||||
echo.
|
||||
echo Architecture: %arch%
|
||||
echo Compiler: %compiler%
|
||||
echo.
|
||||
echo CONFIG: %CONFIG%
|
||||
echo KLAYOUT_VERSION: %KLAYOUT_VERSION%
|
||||
echo KLAYOUT_VERSION_DATE: %KLAYOUT_VERSION_DATE%
|
||||
echo KLAYOUT_VERSION_REV: %KLAYOUT_VERSION_REV%
|
||||
echo HAVE_QTBINDINGS: %HAVE_QTBINDINGS%
|
||||
echo HAVE_QT: %HAVE_QT%
|
||||
echo HAVE_64BIT_COORD: %HAVE_64BIT_COORD%
|
||||
echo HAVE_PYTHON: %HAVE_PYTHON%
|
||||
echo HAVE_RUBY: %HAVE_RUBY%
|
||||
echo MAKE_OPT: %MAKE_OPT%
|
||||
echo.
|
||||
echo qmake binary: %option-qmake%
|
||||
echo Build directory: %option-build%
|
||||
echo Installation directory: %option-bin%
|
||||
|
||||
if %dry_run% equ 1 (
|
||||
echo.
|
||||
echo Dry run ... stopping now.
|
||||
goto :eof
|
||||
)
|
||||
|
||||
rem ----------------------------------------------------------
|
||||
rem Run qmake
|
||||
|
||||
set "inst_path=%~dp0"
|
||||
mkdir "%option-build%" 2>nul
|
||||
cd "%option-build%"
|
||||
if not exist "%option-build%" (
|
||||
echo ERROR: build directory does not exists and cannot be created
|
||||
goto :eof
|
||||
)
|
||||
|
||||
echo on
|
||||
"%option-qmake%" ^
|
||||
HAVE_QT5=1 ^
|
||||
-recursive ^
|
||||
-spec win32-msvc ^
|
||||
"CONFIG+=%CONFIG%" ^
|
||||
"KLAYOUT_VERSION=%KLAYOUT_VERSION%" ^
|
||||
"KLAYOUT_VERSION_DATE=%KLAYOUT_VERSION_DATE%" ^
|
||||
"KLAYOUT_VERSION_REV=%KLAYOUT_VERSION_REV%" ^
|
||||
"HAVE_QTBINDINGS=%HAVE_QTBINDINGS%" ^
|
||||
"HAVE_QT=%HAVE_QT%" ^
|
||||
"HAVE_RUBY=%HAVE_RUBY%" ^
|
||||
"HAVE_PYTHON=%HAVE_PYTHON%" ^
|
||||
"HAVE_64BIT_COORD=%HAVE_64BIT_COORD%" ^
|
||||
"PREFIX=%option-bin%" ^
|
||||
"BITS_PATH=%option-bits%\%compiler%\%arch%" ^
|
||||
%inst_path%\src\klayout.pro ^
|
||||
&& nmake %MAKE_OPT% ^
|
||||
&& nmake install
|
||||
17
setup.py
17
setup.py
|
|
@ -344,12 +344,11 @@ rdb = Extension(config.root + '.rdb',
|
|||
# Core setup function
|
||||
|
||||
if __name__ == '__main__':
|
||||
print("Number of cores", N_cores)
|
||||
setup(name=config.root,
|
||||
version=config.version(),
|
||||
description='KLayout standalone Python package',
|
||||
author='Matthias Koefferlein',
|
||||
author_email='matthias@klayout.de',
|
||||
packages=[config.root],
|
||||
package_dir={config.root: 'src/pymod/distutils_src'},
|
||||
ext_modules=[_tl, _gsi, _pya, _db, _rdb] + db_plugins + [tl, db, rdb])
|
||||
setup(name = config.root,
|
||||
version = config.version(),
|
||||
description = 'KLayout standalone Python package',
|
||||
author = 'Matthias Koefferlein',
|
||||
author_email = 'matthias@klayout.de',
|
||||
packages = [config.root],
|
||||
package_dir = {config.root: 'src/pymod/distutils_src'},
|
||||
ext_modules = [_tl, _gsi, _pya, _db, _rdb] + db_plugins + [tl, db, rdb])
|
||||
|
|
|
|||
|
|
@ -112,7 +112,7 @@ struct cut_polygon_edge
|
|||
{
|
||||
typedef typename PointType::coord_type coord_type;
|
||||
typedef typename db::edge<coord_type> edge_type;
|
||||
typedef typename db::coord_traits<coord_type>::area_type projection_type;
|
||||
typedef double projection_type;
|
||||
|
||||
cut_polygon_edge ()
|
||||
: contour (-1), index (0), projected (0), point (), last_point ()
|
||||
|
|
@ -179,7 +179,7 @@ public:
|
|||
|
||||
bool operator< (const loose_end_struct<CuttingEdgeType> &other) const
|
||||
{
|
||||
if (proj () != other.proj ()) {
|
||||
if (! db::coord_traits<double>::equal (proj (), other.proj ())) {
|
||||
return proj () < other.proj ();
|
||||
} else {
|
||||
return db::vprod_sign (edge (), other.edge ()) > 0;
|
||||
|
|
@ -196,13 +196,13 @@ static bool _cut_polygon_internal (const PolygonType &input, const Edge &line, C
|
|||
typedef db::edge<coord_type> edge_type;
|
||||
typedef cut_polygon_edge<point_type> cut_polygon_edge_type;
|
||||
typedef cut_polygon_segment<cut_polygon_edge_type> cutting_segment_type;
|
||||
typedef typename db::coord_traits<coord_type>::area_type projection_type;
|
||||
|
||||
bool do_hole_assignment = (input.holes () > 0);
|
||||
std::vector <PolygonType> hull_polygons;
|
||||
std::vector <PolygonType> hole_polygons;
|
||||
|
||||
std::vector<cutting_segment_type> cutting_segments;
|
||||
double line_length = line.double_length ();
|
||||
|
||||
for (unsigned int nc = 0; nc < input.holes () + 1; ++nc) {
|
||||
|
||||
|
|
@ -229,7 +229,7 @@ static bool _cut_polygon_internal (const PolygonType &input, const Edge &line, C
|
|||
int s1 = line.side_of (e.p1 ());
|
||||
int s2 = line.side_of (e.p2 ());
|
||||
|
||||
projection_type p = db::sprod (ip.second - line.p1 (), line.p2 () - line.p1 ());
|
||||
double p = line_length * double (db::vprod (e.p1 () - line.p1 (), e.d ())) / double (db::vprod (line.d (), e.d ()));
|
||||
|
||||
if (s1 < 0 && s2 >= 0) {
|
||||
// right -> left or on edge
|
||||
|
|
|
|||
|
|
@ -2242,3 +2242,19 @@ TEST(403)
|
|||
}
|
||||
}
|
||||
|
||||
// issue 166
|
||||
TEST(404)
|
||||
{
|
||||
db::Polygon poly;
|
||||
std::string s ("(390,0;438,936;176,874;0,832;438,937;541,961;821,102)");
|
||||
tl::Extractor ex (s.c_str ());
|
||||
ex.read (poly);
|
||||
|
||||
std::vector<db::Polygon> sp;
|
||||
db::split_polygon (poly, sp);
|
||||
EXPECT_EQ (sp.size (), size_t (2));
|
||||
if (sp.size () >= 2) {
|
||||
EXPECT_EQ (sp[0].to_string (), "(390,0;438,936;390,925;438,937;541,961;821,102)");
|
||||
EXPECT_EQ (sp[1].to_string (), "(0,832;176,874;390,925)");
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1145,3 +1145,11 @@ TEST(121)
|
|||
opt.max_vertex_count = 4;
|
||||
run_test (_this, "t121.oas.gz", "t121_au.gds.gz", true, opt);
|
||||
}
|
||||
|
||||
// Extreme fracturing by max. points
|
||||
TEST(166)
|
||||
{
|
||||
db::GDS2WriterOptions opt;
|
||||
opt.max_vertex_count = 4;
|
||||
run_test (_this, "t166.oas.gz", "t166_au.gds.gz", false, opt);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -70,17 +70,6 @@ DEFImporter::get_orient (bool optional)
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief A structure describing a via
|
||||
*/
|
||||
struct ViaDesc
|
||||
{
|
||||
ViaDesc () : cell (0) { }
|
||||
|
||||
db::Cell *cell;
|
||||
std::string m1, m2;
|
||||
};
|
||||
|
||||
void
|
||||
DEFImporter::read_polygon (db::Polygon &poly, double scale)
|
||||
{
|
||||
|
|
@ -153,7 +142,7 @@ DEFImporter::do_read (db::Layout &layout)
|
|||
double dbu_mic = 1000.0;
|
||||
double scale = 1.0 / (dbu_mic * layout.dbu ());
|
||||
std::map<int, db::Polygon> styles;
|
||||
std::map<std::string, ViaDesc> via_desc;
|
||||
std::map<std::string, ViaDesc> via_desc = m_lef_importer.vias ();
|
||||
std::map<std::string, std::vector<db::Polygon> > regions;
|
||||
std::list<Group> groups;
|
||||
std::list<std::pair<std::string, db::CellInstArray> > instances;
|
||||
|
|
|
|||
|
|
@ -533,6 +533,24 @@ private:
|
|||
const LEFDEFReaderOptions *mp_tech_comp;
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief A structure describing a via
|
||||
*/
|
||||
struct DB_PLUGIN_PUBLIC ViaDesc
|
||||
{
|
||||
ViaDesc () : cell (0) { }
|
||||
|
||||
/**
|
||||
* @brief The cell representing the via
|
||||
*/
|
||||
db::Cell *cell;
|
||||
|
||||
/**
|
||||
* @brief The names of bottom and top metal respectively
|
||||
*/
|
||||
std::string m1, m2;
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief The LEF importer object
|
||||
*/
|
||||
|
|
|
|||
|
|
@ -458,6 +458,9 @@ LEFImporter::do_read (db::Layout &layout)
|
|||
std::string cellname = "VIA_" + n;
|
||||
db::Cell &cell = layout.cell (layout.add_cell (cellname.c_str ()));
|
||||
|
||||
ViaDesc &via_desc = m_vias[n];
|
||||
via_desc.cell = &cell;
|
||||
|
||||
while (test ("DEFAULT") || test ("TOPOFSTACKONLY"))
|
||||
;
|
||||
test (";");
|
||||
|
|
@ -543,9 +546,9 @@ LEFImporter::do_read (db::Layout &layout)
|
|||
|
||||
} else if (test ("LAYERS")) {
|
||||
|
||||
geometry[0].first = get ();
|
||||
via_desc.m1 = geometry[0].first = get ();
|
||||
geometry[1].first = get ();
|
||||
geometry[2].first = get ();
|
||||
via_desc.m2 = geometry[2].first = get ();
|
||||
|
||||
test (";");
|
||||
|
||||
|
|
|
|||
|
|
@ -86,6 +86,16 @@ public:
|
|||
*/
|
||||
double layer_ext (const std::string &layer, double def_ext = 0.0) const;
|
||||
|
||||
/**
|
||||
* @brief Gets a map of the vias defined in this LEF file
|
||||
*
|
||||
* The map maps the via name to the via description.
|
||||
*/
|
||||
const std::map<std::string, ViaDesc> &vias () const
|
||||
{
|
||||
return m_vias;
|
||||
}
|
||||
|
||||
protected:
|
||||
void do_read (db::Layout &layout);
|
||||
|
||||
|
|
@ -95,6 +105,7 @@ private:
|
|||
std::map<std::string, double> m_default_ext;
|
||||
std::map<std::string, db::Cell *> m_macros_by_name;
|
||||
std::map<std::string, db::Box> m_macro_bboxes_by_name;
|
||||
std::map<std::string, ViaDesc> m_vias;
|
||||
|
||||
std::vector <db::Trans> get_iteration (db::Layout &layout);
|
||||
void read_geometries (db::Layout &layout, db::Cell &cell, LayerPurpose purpose, std::map<std::string, db::Box> *collect_bboxes = 0);
|
||||
|
|
|
|||
|
|
@ -30,7 +30,7 @@
|
|||
|
||||
#include <cstdlib>
|
||||
|
||||
static void run_test (tl::TestBase *_this, const char *lef_dir, const char *filename, const char *au)
|
||||
static void run_test (tl::TestBase *_this, const char *lef_dir, const char *filename, const char *au, bool priv = true)
|
||||
{
|
||||
db::LEFDEFReaderOptions tc;
|
||||
tc.set_via_geometry_datatype (0);
|
||||
|
|
@ -60,7 +60,7 @@ static void run_test (tl::TestBase *_this, const char *lef_dir, const char *file
|
|||
|
||||
if (ex.test ("def:")) {
|
||||
|
||||
std::string fn (tl::testsrc_private ());
|
||||
std::string fn (priv ? tl::testsrc_private () : tl::testsrc ());
|
||||
fn += "/testdata/lefdef/";
|
||||
fn += lef_dir;
|
||||
fn += "/";
|
||||
|
|
@ -73,7 +73,7 @@ static void run_test (tl::TestBase *_this, const char *lef_dir, const char *file
|
|||
|
||||
} else if (ex.test ("lef:")) {
|
||||
|
||||
std::string fn (tl::testsrc_private ());
|
||||
std::string fn (priv ? tl::testsrc_private () : tl::testsrc ());
|
||||
fn += "/testdata/lefdef/";
|
||||
fn += lef_dir;
|
||||
fn += "/";
|
||||
|
|
@ -118,7 +118,7 @@ static void run_test (tl::TestBase *_this, const char *lef_dir, const char *file
|
|||
|
||||
if (au) {
|
||||
|
||||
std::string fn (tl::testsrc_private ());
|
||||
std::string fn (priv ? tl::testsrc_private () : tl::testsrc ());
|
||||
fn += "/testdata/lefdef/";
|
||||
fn += lef_dir;
|
||||
fn += "/";
|
||||
|
|
@ -233,3 +233,8 @@ TEST(19)
|
|||
run_test (_this, "def10", "def:in.def", "au.oas.gz");
|
||||
}
|
||||
|
||||
TEST(20)
|
||||
{
|
||||
run_test (_this, "issue-172", "lef:in.lef+def:in.def", "au.oas.gz", false);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -42,6 +42,9 @@ lib_target.path = $$PREFIX/pymod/klayout
|
|||
# This would be nice:
|
||||
# lib_target.files += $$DESTDIR_PYMOD/$${TARGET}$${PYTHONEXTSUFFIX}
|
||||
# but some Qt versions need this explicitly:
|
||||
lib_target.extra = $(INSTALL_PROGRAM) $$DESTDIR_PYMOD/$${TARGET}$${PYTHONEXTSUFFIX} $(INSTALLROOT)$$PREFIX/pymod/klayout
|
||||
msvc {
|
||||
lib_target.extra = $(INSTALL_PROGRAM) $$shell_path($$DESTDIR_PYMOD/$${TARGET}$${PYTHONEXTSUFFIX}) $$shell_path($(INSTALLROOT)$$PREFIX/pymod/klayout)
|
||||
} else {
|
||||
lib_target.extra = $(INSTALL_PROGRAM) $$DESTDIR_PYMOD/$${TARGET}$${PYTHONEXTSUFFIX} $(INSTALLROOT)$$PREFIX/pymod/klayout
|
||||
}
|
||||
INSTALLS = lib_target
|
||||
|
||||
|
|
|
|||
|
|
@ -35,5 +35,9 @@ init_target.path = $$PREFIX/pymod/klayout
|
|||
# This would be nice:
|
||||
# init_target.files += $$DESTDIR_PYMOD/__init__.py
|
||||
# but some Qt versions need this explicitly:
|
||||
init_target.extra = $(INSTALL_PROGRAM) $$DESTDIR_PYMOD/__init__.py $(INSTALLROOT)$$PREFIX/pymod/klayout
|
||||
msvc {
|
||||
init_target.extra = $(INSTALL_PROGRAM) $$shell_path($$DESTDIR_PYMOD/__init__.py) $$shell_path($(INSTALLROOT)$$PREFIX/pymod/klayout)
|
||||
} else {
|
||||
init_target.extra = $(INSTALL_PROGRAM) $$DESTDIR_PYMOD/__init__.py $(INSTALLROOT)$$PREFIX/pymod/klayout
|
||||
}
|
||||
INSTALLS += init_target
|
||||
|
|
|
|||
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
|
@ -0,0 +1,16 @@
|
|||
VERSION 5.6 ;
|
||||
NAMESCASESENSITIVE ON ;
|
||||
DIVIDERCHAR "/" ;
|
||||
BUSBITCHARS "<>" ;
|
||||
DESIGN SMALL ;
|
||||
UNITS DISTANCE MICRONS 100 ;
|
||||
|
||||
DIEAREA ( -30 -30 ) ( 1030 1030 ) ;
|
||||
|
||||
NETS 1 ;
|
||||
- TOP
|
||||
+ ROUTED M1 ( 0 0 ) ( 1000 * ) M2_M1
|
||||
NEW M2 ( 1000 0 ) ( 1000 1000 ) ;
|
||||
END NETS
|
||||
|
||||
END DESIGN
|
||||
|
|
@ -0,0 +1,40 @@
|
|||
VERSION 5.7 ;
|
||||
NAMESCASESENSITIVE ON ;
|
||||
BUSBITCHARS "[]" ;
|
||||
DIVIDERCHAR "/" ;
|
||||
UNITS
|
||||
DATABASE MICRONS 1000 ;
|
||||
END UNITS
|
||||
|
||||
USEMINSPACING OBS ON ;
|
||||
USEMINSPACING PIN OFF ;
|
||||
CLEARANCEMEASURE EUCLIDEAN ;
|
||||
|
||||
MANUFACTURINGGRID 0.05 ;
|
||||
|
||||
LAYER M1
|
||||
TYPE ROUTING ;
|
||||
DIRECTION HORIZONTAL ;
|
||||
WIDTH 0.2 ;
|
||||
END M1
|
||||
|
||||
LAYER V2
|
||||
TYPE CUT ;
|
||||
END V2
|
||||
|
||||
LAYER M2
|
||||
TYPE ROUTING ;
|
||||
DIRECTION VERTICAL ;
|
||||
WIDTH 0.2 ;
|
||||
END M2
|
||||
|
||||
VIA M2_M1 DEFAULT
|
||||
LAYER M1 ;
|
||||
RECT -0.300 -0.300 0.300 0.300 ;
|
||||
LAYER V2 ;
|
||||
RECT -0.200 -0.200 0.200 0.200 ;
|
||||
LAYER M2 ;
|
||||
RECT -0.300 -0.300 0.300 0.300 ;
|
||||
END M2_M1
|
||||
|
||||
END LIBRARY
|
||||
|
|
@ -150,7 +150,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual( c.is_mirror(), True )
|
||||
self.assertEqual( c.rot(), pya.DCplxTrans.M135.rot() )
|
||||
self.assertEqual( str(c.s_trans()), "m135 0,0" )
|
||||
self.assertEqual( c.angle, 270 )
|
||||
self.assertAlmostEqual( c.angle, 270 )
|
||||
|
||||
self.assertEqual( str(c.trans( pya.Edge(0, 1, 2, 3) )), "(-1,0;-3,-2)" )
|
||||
self.assertEqual( str(( c * pya.Edge(0, 1, 2, 3) )), "(-1,0;-3,-2)" )
|
||||
|
|
@ -174,7 +174,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual( c.is_mirror(), False )
|
||||
self.assertEqual( c.rot(), pya.DCplxTrans.R0.rot() )
|
||||
self.assertEqual( str(c.s_trans()), "r0 0,0" )
|
||||
self.assertEqual( c.angle, 0 )
|
||||
self.assertAlmostEqual( c.angle, 0 )
|
||||
|
||||
c = pya.DCplxTrans( 0.75, 45, True, 2.5, -12.5 )
|
||||
self.assertEqual( str(c), "m22.5 *0.75 2.5,-12.5" )
|
||||
|
|
@ -185,7 +185,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual( c.is_mag(), True )
|
||||
self.assertEqual( c.rot(), pya.DCplxTrans.M0.rot() )
|
||||
self.assertEqual( str(c.s_trans()), "m0 2.5,-12.5" )
|
||||
self.assertEqual( c.angle, 45 )
|
||||
self.assertAlmostEqual( c.angle, 45 )
|
||||
|
||||
self.assertEqual( str(c.ctrans( 5 )), "3.75" )
|
||||
self.assertEqual( str(c.trans( pya.DPoint( 12, 16 ) )), "17.3492424049,-14.6213203436" )
|
||||
|
|
@ -335,7 +335,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual( c.is_mirror(), True )
|
||||
self.assertEqual( c.rot(), pya.CplxTrans.M135.rot() )
|
||||
self.assertEqual( str(c.s_trans()), "m135 0,0" )
|
||||
self.assertEqual( c.angle, 270 )
|
||||
self.assertAlmostEqual( c.angle, 270 )
|
||||
|
||||
c = pya.CplxTrans.from_dtrans( pya.DCplxTrans.M135 )
|
||||
self.assertEqual( str(c), "m135 *1 0,0" )
|
||||
|
|
@ -348,7 +348,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual( c.is_mirror(), False )
|
||||
self.assertEqual( c.rot(), pya.CplxTrans.R0.rot() )
|
||||
self.assertEqual( str(c.s_trans()), "r0 0,0" )
|
||||
self.assertEqual( c.angle, 0 )
|
||||
self.assertAlmostEqual( c.angle, 0 )
|
||||
|
||||
c = pya.CplxTrans( 0.75, 45, True, 2.5, -12.5 )
|
||||
self.assertEqual( str(c), "m22.5 *0.75 2.5,-12.5" )
|
||||
|
|
@ -360,7 +360,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual( c.is_mag(), True )
|
||||
self.assertEqual( c.rot(), pya.CplxTrans.M0.rot() )
|
||||
self.assertEqual( str(c.s_trans()), "m0 3,-13" )
|
||||
self.assertEqual( c.angle, 45 )
|
||||
self.assertAlmostEqual( c.angle, 45 )
|
||||
|
||||
self.assertEqual( str(c.ctrans( 5 )), "3.75" )
|
||||
self.assertEqual( str(c.trans( pya.Point( 12, 16 ) )), "17.3492424049,-14.6213203436" )
|
||||
|
|
@ -517,7 +517,7 @@ class DBTransTests(unittest.TestCase):
|
|||
self.assertEqual(t1 < t4, True)
|
||||
self.assertEqual(t4 < t1, False)
|
||||
|
||||
# Hash values
|
||||
# Hash values
|
||||
def test_5_Trans_Hash(self):
|
||||
|
||||
t1 = pya.DTrans( pya.DTrans.M135, pya.DPoint( 17, 5 ))
|
||||
|
|
|
|||
|
|
@ -471,9 +471,11 @@ class QtBindingTest(unittest.TestCase):
|
|||
|
||||
pya.QApplication.processEvents()
|
||||
|
||||
s1 = "QKeyEvent: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)\nQKeyEvent: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)\nQKeyEvent: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)"
|
||||
s2 = "QKeyEvent: KeyPress (6)\nQKeyEvent: KeyPress (6)\nQKeyEvent: KeyPress (6)"
|
||||
self.assertEqual("\n".join(ef.log()) == s1 or "\n".join(ef.log()) == s2, True)
|
||||
s1 = "QKeyEvent: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)\nQKeyEvent: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)\nQKeyEvent: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)"
|
||||
s2 = "QKeyEvent: KeyPress (6)\nQKeyEvent: KeyPress (6)\nQKeyEvent: KeyPress (6)"
|
||||
s3 = "QKeyEvent_Native: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)\nQKeyEvent_Native: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)\nQKeyEvent_Native: ShortcutOverride (51)\nQKeyEvent: KeyPress (6)"
|
||||
self.assertIn("\n".join(ef.log()), (s1, s2, s3))
|
||||
|
||||
ef = None
|
||||
|
||||
self.assertEqual(widget.text, "ABCpO")
|
||||
|
|
|
|||
|
|
@ -534,7 +534,10 @@ class QtBinding_TestClass < TestBase
|
|||
|
||||
GC.start
|
||||
|
||||
assert_equal(ef.log.select { |s| s !~ /RBA::QKeyEvent: ShortcutOverride/ }.join("\n"), "RBA::QKeyEvent: KeyPress (6)\nRBA::QKeyEvent: KeyPress (6)\nRBA::QKeyEvent: KeyPress (6)")
|
||||
assert_equal(ef.log.select { |s| s !~ /RBA::QKeyEvent: ShortcutOverride/ }.join("\n"), "RBA::QKeyEvent: KeyPress (6)\nRBA::QKeyEvent: KeyPress (6)\nRBA::QKeyEvent: KeyPress (6)")
|
||||
|
||||
# TODO: on macOS 10.13, ef.log yields "RBA::QKeyEvent_Native: ShortcutOverride (51)\nRBA::QKeyEvent: KeyPress (6)\nRBA::QKeyEvent_Native: ShortcutOverride (51)\nRBA::QKeyEvent: KeyPress (6)\nRBA::QKeyEvent_Native: ShortcutOverride (51)\nRBA::QKeyEvent: KeyPress (6)", causing this test to fail.
|
||||
|
||||
ef = nil
|
||||
ef = EventFilter::new
|
||||
GC.start
|
||||
|
|
|
|||
Loading…
Reference in New Issue