Add support for reading gzip'd input files
authorDavid Shah <dave@ds0.me>
Fri, 26 Jul 2019 09:23:58 +0000 (10:23 +0100)
committerDavid Shah <dave@ds0.me>
Fri, 26 Jul 2019 09:23:58 +0000 (10:23 +0100)
Signed-off-by: David Shah <dave@ds0.me>
.travis.yml
Makefile
README.md
kernel/register.cc
tests/various/gzip_verilog.v.gz [new file with mode: 0644]
tests/various/gzip_verilog.ys [new file with mode: 0644]

index 957735f1dc110dd60e9ec78ca6b3b843eda246f3..4102f05feb79b62a62a82f6272522fee79bc67f2 100644 (file)
@@ -36,6 +36,7 @@ matrix:
             - libboost-system-dev
             - libboost-python-dev
             - libboost-filesystem-dev
+            - zlib1g-dev
       env:
         - MATRIX_EVAL="CONFIG=gcc && CC=gcc-4.8 && CXX=g++-4.8"
 
@@ -64,6 +65,7 @@ matrix:
             - libboost-system-dev
             - libboost-python-dev
             - libboost-filesystem-dev
+            - zlib1g-dev
       env:
         - MATRIX_EVAL="CONFIG=gcc && CC=gcc-6 && CXX=g++-6"
 
@@ -92,6 +94,7 @@ matrix:
             - libboost-system-dev
             - libboost-python-dev
             - libboost-filesystem-dev
+            - zlib1g-dev
       env:
         - MATRIX_EVAL="CONFIG=gcc && CC=gcc-7 && CXX=g++-7"
 
@@ -121,6 +124,7 @@ matrix:
             - libboost-system-dev
             - libboost-python-dev
             - libboost-filesystem-dev
+            - zlib1g-dev
       env:
         - MATRIX_EVAL="CONFIG=clang && CC=clang-3.8 && CXX=clang++-3.8"
 
@@ -149,6 +153,7 @@ matrix:
             - libboost-system-dev
             - libboost-python-dev
             - libboost-filesystem-dev
+            - zlib1g-dev
       env:
         - MATRIX_EVAL="CONFIG=clang && CC=clang-5.0 && CXX=clang++-5.0"
 
index d33f27b639024d614adf9e9327427df1c2c410e4..ea804e0d5b79d2b66947a8145ec823064d722fb7 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -19,6 +19,7 @@ ENABLE_VERIFIC := 0
 ENABLE_COVER := 1
 ENABLE_LIBYOSYS := 0
 ENABLE_PROTOBUF := 0
+ENABLE_ZLIB := 1
 
 # python wrappers
 ENABLE_PYOSYS := 0
@@ -384,6 +385,12 @@ ifeq ($(ENABLE_GLOB),1)
 CXXFLAGS += -DYOSYS_ENABLE_GLOB
 endif
 
+ifeq ($(ENABLE_ZLIB),1)
+CXXFLAGS += -DYOSYS_ENABLE_ZLIB
+LDLIBS += -lz
+endif
+
+
 ifeq ($(ENABLE_TCL),1)
 TCL_VERSION ?= tcl$(shell bash -c "tclsh <(echo 'puts [info tclversion]')")
 ifeq ($(OS), FreeBSD)
index 9e221be3827a279b1ba111734e039841f09eb9d0..2a708130416dd87e2affdadb86ac0b4ed4269e81 100644 (file)
--- a/README.md
+++ b/README.md
@@ -67,13 +67,13 @@ prerequisites for building yosys:
        $ sudo apt-get install build-essential clang bison flex \
                libreadline-dev gawk tcl-dev libffi-dev git \
                graphviz xdot pkg-config python3 libboost-system-dev \
-               libboost-python-dev libboost-filesystem-dev
+               libboost-python-dev libboost-filesystem-dev zlib1g-dev
 
 Similarily, on Mac OS X MacPorts or Homebrew can be used to install dependencies:
 
        $ brew tap Homebrew/bundle && brew bundle
        $ sudo port install bison flex readline gawk libffi \
-               git graphviz pkgconfig python36 boost
+               git graphviz pkgconfig python36 boost zlib
 
 On FreeBSD use the following command to install all prerequisites:
 
@@ -85,7 +85,7 @@ On FreeBSD system use gmake instead of make. To run tests use:
 
 For Cygwin use the following command to install all prerequisites, or select these additional packages:
 
-       setup-x86_64.exe -q --packages=bison,flex,gcc-core,gcc-g++,git,libffi-devel,libreadline-devel,make,pkg-config,python3,tcl-devel,boost-build
+       setup-x86_64.exe -q --packages=bison,flex,gcc-core,gcc-g++,git,libffi-devel,libreadline-devel,make,pkg-config,python3,tcl-devel,boost-build,zlib-devel
 
 There are also pre-compiled Yosys binary packages for Ubuntu and Win32 as well
 as a source distribution for Visual Studio. Visit the Yosys download page for
index 26da96b95b6d9e62a217f3577050a25d510c4d38..4f1501330364dfacaba471c5e239de75222a23ad 100644 (file)
 #include <stdio.h>
 #include <errno.h>
 
+#ifdef YOSYS_ENABLE_ZLIB
+#include <zlib.h>
+
+PRIVATE_NAMESPACE_BEGIN
+#define GZ_BUFFER_SIZE 8192
+void decompress_gzip(const std::string &filename, std::stringstream &out)
+{
+       char buffer[GZ_BUFFER_SIZE];
+       int bytes_read;
+       gzFile gzf = gzopen(filename.c_str(), "rb");
+       while(!gzeof(gzf)) {
+               bytes_read = gzread(gzf, reinterpret_cast<void *>(buffer), GZ_BUFFER_SIZE);
+               out.write(buffer, bytes_read);
+       }
+       gzclose(gzf);
+}
+PRIVATE_NAMESPACE_END
+
+#endif
+
 YOSYS_NAMESPACE_BEGIN
 
 #define MAX_REG_COUNT 1000
@@ -436,6 +456,26 @@ void Frontend::extra_args(std::istream *&f, std::string &filename, std::vector<s
                                delete ff;
                        else
                                f = ff;
+                       // Check for gzip magic
+                       unsigned char magic[3];
+                       int n = readsome(*ff, reinterpret_cast<char*>(magic), 3);
+                       if (n == 3 && magic[0] == 0x1f && magic[1] == 0x8b) {
+#ifdef YOSYS_ENABLE_ZLIB
+                               log("Found gzip magic in file `%s', decompressing using zlib.\n", filename.c_str());
+                               if (magic[2] != 8)
+                                       log_cmd_error("gzip file `%s' uses unsupported compression type %02x\n",
+                                               filename.c_str(), unsigned(magic[2]));
+                               delete ff;
+                               std::stringstream *df = new std::stringstream();
+                               decompress_gzip(filename, *df);
+                               f = df;
+#else
+                               log_cmd_error("File `%s' is a gzip file, but Yosys is compiled without zlib.\n", filename.c_str());
+#endif
+                       } else {
+                               ff->clear();
+                               ff->seekg(0, std::ios::beg);
+                       }
                }
                if (f == NULL)
                        log_cmd_error("Can't open input file `%s' for reading: %s\n", filename.c_str(), strerror(errno));
diff --git a/tests/various/gzip_verilog.v.gz b/tests/various/gzip_verilog.v.gz
new file mode 100644 (file)
index 0000000..c52a953
Binary files /dev/null and b/tests/various/gzip_verilog.v.gz differ
diff --git a/tests/various/gzip_verilog.ys b/tests/various/gzip_verilog.ys
new file mode 100644 (file)
index 0000000..870317e
--- /dev/null
@@ -0,0 +1,2 @@
+read_verilog gzip_verilog.v.gz
+select -assert-any top