From 1eb99bf05849e3108129d32eaacaa40c9e266c4b Mon Sep 17 00:00:00 2001 From: Luigi Scarso Date: Sat, 15 Feb 2020 12:45:08 +0000 Subject: sync with luatex rev. 7287 git-svn-id: svn://tug.org/texlive/trunk@53789 c570f23f-e606-0410-a88d-b1316a301751 --- Build/source/texk/web2c/luatexdir/ChangeLog | 39 + Build/source/texk/web2c/luatexdir/am/libluatex.am | 10 +- Build/source/texk/web2c/luatexdir/am/luapplib.am | 107 +- Build/source/texk/web2c/luatexdir/am/luatex.am | 4 +- Build/source/texk/web2c/luatexdir/font/luafont.c | 213 +- .../source/texk/web2c/luatexdir/font/luatexfont.h | 4 +- .../luatexdir/font/pdfglyphtounicode-luatex.c | 106 + .../luatexdir/font/pdfglyphtounicode-pdftex.c | 126 + .../luatexdir/font/pdfglyphtounicode-readme.txt | 10 + Build/source/texk/web2c/luatexdir/font/texfont.h | 1 - Build/source/texk/web2c/luatexdir/font/vfpacket.c | 3 + Build/source/texk/web2c/luatexdir/image/epdf.h | 3 +- .../source/texk/web2c/luatexdir/image/pdftoepdf.c | 39 +- Build/source/texk/web2c/luatexdir/image/writeimg.h | 2 +- .../source/texk/web2c/luatexdir/lua/lcallbacklib.c | 14 + .../texk/web2c/luatexdir/lua/lepdflib.cc.orig | 2939 ++++++ Build/source/texk/web2c/luatexdir/lua/lfontlib.c | 16 +- .../source/texk/web2c/luatexdir/lua/lnewtokenlib.c | 9 +- Build/source/texk/web2c/luatexdir/lua/lpdfelib.c | 44 +- .../texk/web2c/luatexdir/lua/lpdfscannerlib.c | 2 +- Build/source/texk/web2c/luatexdir/lua/luainit.c | 2 + Build/source/texk/web2c/luatexdir/lua/luatex-api.h | 2 +- .../texk/web2c/luatexdir/luaharfbuzz/README-win.md | 53 - .../texk/web2c/luatexdir/luaharfbuzz/README.md | 19 +- .../texk/web2c/luatexdir/luaharfbuzz/config.ld | 2 +- .../luaharfbuzz/docs/examples/core_types.lua.html | 2 +- .../docs/examples/custom_callbacks.lua.html | 85 - .../docs/examples/harfbuzz_setup.lua.html | 231 - .../docs/examples/ot_font_loader.lua.html | 139 - .../docs/examples/package_path_searcher.lua.html | 104 - .../web2c/luatexdir/luaharfbuzz/docs/index.html | 12 +- .../fonts/TwitterColorEmoji-SVGinOT.ttf | Bin 0 -> 4232 bytes .../luaharfbuzz/luaharfbuzz-1.0.0-1.rockspec | 51 - .../luaharfbuzz/luaharfbuzz-1.1.0-1.rockspec | 46 + .../luaharfbuzz/luaharfbuzz-scm-1.rockspec | 5 +- .../luatexdir/luaharfbuzz/spec/buffer_spec.lua | 55 + .../luatexdir/luaharfbuzz/spec/harfbuzz_spec.lua | 42 +- .../luatexdir/luaharfbuzz/src/harfbuzz.luadoc | 10 +- .../luatexdir/luaharfbuzz/src/luaharfbuzz/buffer.c | 116 +- .../luatexdir/luaharfbuzz/src/luaharfbuzz/face.c | 27 + .../luaharfbuzz/src/luaharfbuzz/feature.c | 69 + .../luatexdir/luaharfbuzz/src/luaharfbuzz/font.c | 2 +- .../luaharfbuzz/src/luaharfbuzz/luaharfbuzz.c | 28 +- .../luatexdir/luaharfbuzz/status/full_api.txt | 142 +- Build/source/texk/web2c/luatexdir/luamd5/md5lib.c | 10 +- Build/source/texk/web2c/luatexdir/luapeg/lpeg.c | 2 +- .../texk/web2c/luatexdir/luapplib/.gitattributes | 10 + .../texk/web2c/luatexdir/luapplib/.gitignore | 8 + .../texk/web2c/luatexdir/luapplib/.gitmodules | 3 + .../texk/web2c/luatexdir/luapplib/.travis.yml | 20 + .../texk/web2c/luatexdir/luapplib/CMakeLists.txt | 6 + .../texk/web2c/luatexdir/luapplib/Makefile.orig | 89 - .../source/texk/web2c/luatexdir/luapplib/README.md | 9 + .../web2c/luatexdir/luapplib/azure-pipelines.yml | 36 + .../texk/web2c/luatexdir/luapplib/doc/Makefile | 20 + .../doc/_build/doctrees/environment.pickle | Bin 0 -> 32928 bytes .../luapplib/doc/_build/doctrees/ppapi-1.x.doctree | Bin 0 -> 167607 bytes .../luapplib/doc/_build/doctrees/ppapi-2.x.doctree | Bin 0 -> 167117 bytes .../luapplib/doc/_build/doctrees/ppapi.doctree | Bin 0 -> 165058 bytes .../luapplib/doc/_build/doctrees/ppcode.doctree | Bin 0 -> 64496 bytes .../luapplib/doc/_build/doctrees/pplib.doctree | Bin 0 -> 3371 bytes .../luapplib/doc/_build/doctrees/ppnew.doctree | Bin 0 -> 25753 bytes .../luatexdir/luapplib/doc/_build/html/.buildinfo | 4 + .../doc/_build/html/_sources/ppapi-1.x.rst.txt | 937 ++ .../doc/_build/html/_sources/ppapi-2.x.rst.txt | 937 ++ .../doc/_build/html/_sources/ppapi.rst.txt | 937 ++ .../doc/_build/html/_sources/ppcode.rst.txt | 101 + .../doc/_build/html/_sources/pplib.rst.txt | 15 + .../doc/_build/html/_sources/ppnew.rst.txt | 103 + .../doc/_build/html/_static/ajax-loader.gif | Bin 0 -> 673 bytes .../doc/_build/html/_static/background_b01.png | Bin 0 -> 78 bytes .../luapplib/doc/_build/html/_static/basic.css | 676 ++ .../luapplib/doc/_build/html/_static/bizstyle.css | 490 + .../luapplib/doc/_build/html/_static/bizstyle.js | 41 + .../doc/_build/html/_static/comment-bright.png | Bin 0 -> 756 bytes .../doc/_build/html/_static/comment-close.png | Bin 0 -> 829 bytes .../luapplib/doc/_build/html/_static/comment.png | Bin 0 -> 641 bytes .../doc/_build/html/_static/css3-mediaqueries.js | 1 + .../_build/html/_static/css3-mediaqueries_src.js | 1104 ++ .../luapplib/doc/_build/html/_static/doctools.js | 315 + .../_build/html/_static/documentation_options.js | 10 + .../doc/_build/html/_static/down-pressed.png | Bin 0 -> 222 bytes .../luapplib/doc/_build/html/_static/down.png | Bin 0 -> 202 bytes .../luapplib/doc/_build/html/_static/file.png | Bin 0 -> 286 bytes .../doc/_build/html/_static/jquery-3.2.1.js | 10253 +++++++++++++++++++ .../luapplib/doc/_build/html/_static/jquery.js | 4 + .../doc/_build/html/_static/language_data.js | 297 + .../luapplib/doc/_build/html/_static/minus.png | Bin 0 -> 90 bytes .../luapplib/doc/_build/html/_static/plus.png | Bin 0 -> 90 bytes .../luapplib/doc/_build/html/_static/pygments.css | 69 + .../doc/_build/html/_static/searchtools.js | 481 + .../doc/_build/html/_static/underscore-1.3.1.js | 999 ++ .../luapplib/doc/_build/html/_static/underscore.js | 31 + .../doc/_build/html/_static/up-pressed.png | Bin 0 -> 214 bytes .../luapplib/doc/_build/html/_static/up.png | Bin 0 -> 203 bytes .../luapplib/doc/_build/html/_static/websupport.js | 808 ++ .../luapplib/doc/_build/html/genindex.html | 85 + .../luatexdir/luapplib/doc/_build/html/objects.inv | 6 + .../luapplib/doc/_build/html/ppapi-1.x.html | 1030 ++ .../luapplib/doc/_build/html/ppapi-2.x.html | 1031 ++ .../luatexdir/luapplib/doc/_build/html/ppapi.html | 1030 ++ .../luatexdir/luapplib/doc/_build/html/ppcode.html | 996 ++ .../luatexdir/luapplib/doc/_build/html/pplib.html | 176 + .../luatexdir/luapplib/doc/_build/html/ppnew.html | 209 + .../luatexdir/luapplib/doc/_build/html/search.html | 97 + .../luapplib/doc/_build/html/searchindex.js | 1 + .../texk/web2c/luatexdir/luapplib/doc/conf.py | 156 + .../texk/web2c/luatexdir/luapplib/doc/make.bat | 36 + .../web2c/luatexdir/luapplib/doc/ppapi-1.x.rst | 937 ++ .../web2c/luatexdir/luapplib/doc/ppapi-2.x.rst | 937 ++ .../texk/web2c/luatexdir/luapplib/doc/ppcode.rst | 101 + .../texk/web2c/luatexdir/luapplib/doc/pplib.rst | 15 + .../texk/web2c/luatexdir/luapplib/doc/ppnew.rst | 103 + .../texk/web2c/luatexdir/luapplib/html/.buildinfo | 4 - .../luatexdir/luapplib/html/_sources/ppapi.rst.txt | 937 -- .../luapplib/html/_sources/ppcode.rst.txt | 64 - .../luatexdir/luapplib/html/_sources/pplib.rst.txt | 13 - .../luapplib/html/_static/ajax-loader.gif | Bin 673 -> 0 bytes .../luapplib/html/_static/background_b01.png | Bin 78 -> 0 bytes .../luatexdir/luapplib/html/_static/basic.css | 665 -- .../luatexdir/luapplib/html/_static/bizstyle.css | 490 - .../luatexdir/luapplib/html/_static/bizstyle.js | 41 - .../luapplib/html/_static/comment-bright.png | Bin 756 -> 0 bytes .../luapplib/html/_static/comment-close.png | Bin 829 -> 0 bytes .../luatexdir/luapplib/html/_static/comment.png | Bin 641 -> 0 bytes .../luapplib/html/_static/css3-mediaqueries.js | 1 - .../luapplib/html/_static/css3-mediaqueries_src.js | 1104 -- .../luatexdir/luapplib/html/_static/doctools.js | 313 - .../luapplib/html/_static/documentation_options.js | 9 - .../luapplib/html/_static/down-pressed.png | Bin 222 -> 0 bytes .../web2c/luatexdir/luapplib/html/_static/down.png | Bin 202 -> 0 bytes .../web2c/luatexdir/luapplib/html/_static/file.png | Bin 286 -> 0 bytes .../luapplib/html/_static/jquery-3.2.1.js | 10253 ------------------- .../luatexdir/luapplib/html/_static/jquery.js | 4 - .../luatexdir/luapplib/html/_static/minus.png | Bin 90 -> 0 bytes .../web2c/luatexdir/luapplib/html/_static/plus.png | Bin 90 -> 0 bytes .../luatexdir/luapplib/html/_static/pygments.css | 69 - .../luatexdir/luapplib/html/_static/searchtools.js | 761 -- .../luapplib/html/_static/underscore-1.3.1.js | 999 -- .../luatexdir/luapplib/html/_static/underscore.js | 31 - .../luatexdir/luapplib/html/_static/up-pressed.png | Bin 214 -> 0 bytes .../web2c/luatexdir/luapplib/html/_static/up.png | Bin 203 -> 0 bytes .../luatexdir/luapplib/html/_static/websupport.js | 808 -- .../web2c/luatexdir/luapplib/html/genindex.html | 83 - .../texk/web2c/luatexdir/luapplib/html/objects.inv | 6 - .../texk/web2c/luatexdir/luapplib/html/ppapi.html | 1028 -- .../texk/web2c/luatexdir/luapplib/html/ppcode.html | 923 -- .../texk/web2c/luatexdir/luapplib/html/pplib.html | 140 - .../texk/web2c/luatexdir/luapplib/html/search.html | 94 - .../web2c/luatexdir/luapplib/html/searchindex.js | 1 - Build/source/texk/web2c/luatexdir/luapplib/ppapi.h | 419 - .../source/texk/web2c/luatexdir/luapplib/pparray.c | 146 - .../source/texk/web2c/luatexdir/luapplib/pparray.h | 7 - .../source/texk/web2c/luatexdir/luapplib/ppconf.h | 86 - .../source/texk/web2c/luatexdir/luapplib/ppcrypt.c | 519 - .../texk/web2c/luatexdir/luapplib/ppcrypt.c.orig | 628 -- .../source/texk/web2c/luatexdir/luapplib/ppcrypt.h | 67 - .../source/texk/web2c/luatexdir/luapplib/ppdict.c | 163 - .../source/texk/web2c/luatexdir/luapplib/ppdict.h | 7 - .../texk/web2c/luatexdir/luapplib/ppfilter.h | 10 - .../source/texk/web2c/luatexdir/luapplib/ppheap.c | 435 - .../source/texk/web2c/luatexdir/luapplib/ppheap.h | 29 - Build/source/texk/web2c/luatexdir/luapplib/pplib.h | 23 - .../source/texk/web2c/luatexdir/luapplib/ppload.c | 2753 ----- .../source/texk/web2c/luatexdir/luapplib/ppload.h | 54 - .../texk/web2c/luatexdir/luapplib/ppstream.c | 489 - .../texk/web2c/luatexdir/luapplib/ppstream.h | 10 - .../source/texk/web2c/luatexdir/luapplib/pptest1.c | 86 - .../source/texk/web2c/luatexdir/luapplib/pptest2.c | 139 - .../source/texk/web2c/luatexdir/luapplib/pptest3.c | 98 - .../source/texk/web2c/luatexdir/luapplib/ppxref.c | 196 - .../source/texk/web2c/luatexdir/luapplib/ppxref.h | 35 - .../web2c/luatexdir/luapplib/src/CMakeLists.txt | 151 + .../texk/web2c/luatexdir/luapplib/src/Makefile | 99 + .../texk/web2c/luatexdir/luapplib/src/Makefile.vc | 98 + .../texk/web2c/luatexdir/luapplib/src/ppapi.h | 404 + .../texk/web2c/luatexdir/luapplib/src/pparray.c | 145 + .../texk/web2c/luatexdir/luapplib/src/pparray.h | 7 + .../texk/web2c/luatexdir/luapplib/src/ppconf.h | 76 + .../texk/web2c/luatexdir/luapplib/src/ppcrypt.c | 525 + .../texk/web2c/luatexdir/luapplib/src/ppcrypt.h | 67 + .../texk/web2c/luatexdir/luapplib/src/ppdict.c | 166 + .../texk/web2c/luatexdir/luapplib/src/ppdict.h | 7 + .../texk/web2c/luatexdir/luapplib/src/ppfilter.h | 10 + .../texk/web2c/luatexdir/luapplib/src/ppheap.c | 40 + .../texk/web2c/luatexdir/luapplib/src/ppheap.h | 46 + .../texk/web2c/luatexdir/luapplib/src/pplib.h | 22 + .../texk/web2c/luatexdir/luapplib/src/ppload.c | 2769 +++++ .../texk/web2c/luatexdir/luapplib/src/ppload.h | 58 + .../texk/web2c/luatexdir/luapplib/src/ppstream.c | 491 + .../texk/web2c/luatexdir/luapplib/src/ppstream.h | 10 + .../texk/web2c/luatexdir/luapplib/src/pptest1.c | 104 + .../texk/web2c/luatexdir/luapplib/src/pptest2.c | 138 + .../texk/web2c/luatexdir/luapplib/src/pptest3.c | 123 + .../texk/web2c/luatexdir/luapplib/src/ppxref.c | 215 + .../texk/web2c/luatexdir/luapplib/src/ppxref.h | 35 + .../web2c/luatexdir/luapplib/src/util/README.md | 8 + .../web2c/luatexdir/luapplib/src/util/utilbasexx.c | 1742 ++++ .../web2c/luatexdir/luapplib/src/util/utilbasexx.h | 111 + .../web2c/luatexdir/luapplib/src/util/utilcrypt.c | 1190 +++ .../web2c/luatexdir/luapplib/src/util/utilcrypt.h | 90 + .../luatexdir/luapplib/src/util/utilcryptdef.h | 32 + .../web2c/luatexdir/luapplib/src/util/utildecl.h | 28 + .../web2c/luatexdir/luapplib/src/util/utilflate.c | 322 + .../web2c/luatexdir/luapplib/src/util/utilflate.h | 21 + .../web2c/luatexdir/luapplib/src/util/utilfpred.c | 778 ++ .../web2c/luatexdir/luapplib/src/util/utilfpred.h | 23 + .../web2c/luatexdir/luapplib/src/util/utiliof.c | 2993 ++++++ .../web2c/luatexdir/luapplib/src/util/utiliof.h | 673 ++ .../web2c/luatexdir/luapplib/src/util/utillog.c | 60 + .../web2c/luatexdir/luapplib/src/util/utillog.h | 10 + .../web2c/luatexdir/luapplib/src/util/utillzw.c | 705 ++ .../web2c/luatexdir/luapplib/src/util/utillzw.h | 30 + .../web2c/luatexdir/luapplib/src/util/utilmd5.c | 447 + .../web2c/luatexdir/luapplib/src/util/utilmd5.h | 49 + .../web2c/luatexdir/luapplib/src/util/utilmem.c | 67 + .../web2c/luatexdir/luapplib/src/util/utilmem.h | 16 + .../luatexdir/luapplib/src/util/utilmemallc.h | 561 + .../luatexdir/luapplib/src/util/utilmemallh.h | 26 + .../luatexdir/luapplib/src/util/utilmemheap.c | 994 ++ .../luatexdir/luapplib/src/util/utilmemheap.h | 179 + .../luatexdir/luapplib/src/util/utilmemheapiof.c | 192 + .../luatexdir/luapplib/src/util/utilmemheapiof.h | 18 + .../luatexdir/luapplib/src/util/utilmeminfo.c | 38 + .../luatexdir/luapplib/src/util/utilmeminfo.h | 9 + .../web2c/luatexdir/luapplib/src/util/utilnumber.c | 1177 +++ .../web2c/luatexdir/luapplib/src/util/utilnumber.h | 428 + .../web2c/luatexdir/luapplib/src/util/utilplat.h | 31 + .../web2c/luatexdir/luapplib/src/util/utilsha.c | 1065 ++ .../web2c/luatexdir/luapplib/src/util/utilsha.h | 79 + .../texk/web2c/luatexdir/luapplib/util/utilarm.h | 10 - .../web2c/luatexdir/luapplib/util/utilbasexx.c | 2108 ---- .../web2c/luatexdir/luapplib/util/utilbasexx.h | 133 - .../texk/web2c/luatexdir/luapplib/util/utilcrypt.c | 1191 --- .../texk/web2c/luatexdir/luapplib/util/utilcrypt.h | 90 - .../web2c/luatexdir/luapplib/util/utilcryptdef.h | 30 - .../texk/web2c/luatexdir/luapplib/util/utildecl.h | 28 - .../texk/web2c/luatexdir/luapplib/util/utilflate.c | 319 - .../texk/web2c/luatexdir/luapplib/util/utilflate.h | 21 - .../texk/web2c/luatexdir/luapplib/util/utilfpred.c | 772 -- .../texk/web2c/luatexdir/luapplib/util/utilfpred.h | 23 - .../texk/web2c/luatexdir/luapplib/util/utiliof.c | 2951 ------ .../texk/web2c/luatexdir/luapplib/util/utiliof.h | 669 -- .../texk/web2c/luatexdir/luapplib/util/utillog.c | 60 - .../texk/web2c/luatexdir/luapplib/util/utillog.h | 10 - .../texk/web2c/luatexdir/luapplib/util/utillzw.c | 701 -- .../texk/web2c/luatexdir/luapplib/util/utillzw.h | 30 - .../texk/web2c/luatexdir/luapplib/util/utilmd5.c | 413 - .../web2c/luatexdir/luapplib/util/utilmd5.c.orig | 413 - .../texk/web2c/luatexdir/luapplib/util/utilmd5.h | 115 - .../web2c/luatexdir/luapplib/util/utilmd5.h.orig | 115 - .../texk/web2c/luatexdir/luapplib/util/utilmem.c | 68 - .../texk/web2c/luatexdir/luapplib/util/utilmem.h | 59 - .../web2c/luatexdir/luapplib/util/utilnumber.c | 1325 --- .../web2c/luatexdir/luapplib/util/utilnumber.h | 354 - .../texk/web2c/luatexdir/luapplib/util/utilplat.h | 23 - .../texk/web2c/luatexdir/luapplib/util/utilsha.c | 1287 --- .../texk/web2c/luatexdir/luapplib/util/utilsha.h | 134 - Build/source/texk/web2c/luatexdir/luatex.c | 6 +- .../texk/web2c/luatexdir/luatex_svnversion.h | 2 +- Build/source/texk/web2c/luatexdir/pdf/pdftables.c | 1 - Build/source/texk/web2c/luatexdir/pdf/pdftables.h | 2 +- Build/source/texk/web2c/luatexdir/tex/filename.c | 4 + Build/source/texk/web2c/luatexdir/tex/linebreak.c | 17 +- .../source/texk/web2c/luatexdir/tex/maincontrol.c | 2 - .../texk/web2c/luatexdir/tex/postlinebreak.c | 2 + Build/source/texk/web2c/luatexdir/tex/texmath.c | 6 +- Build/source/texk/web2c/luatexdir/tex/texnodes.c | 3 +- Build/source/texk/web2c/luatexdir/tex/textoken.c | 2 +- 269 files changed, 49802 insertions(+), 39642 deletions(-) create mode 100644 Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-luatex.c create mode 100644 Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-pdftex.c create mode 100644 Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-readme.txt create mode 100644 Build/source/texk/web2c/luatexdir/lua/lepdflib.cc.orig delete mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/README-win.md delete mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/custom_callbacks.lua.html delete mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/harfbuzz_setup.lua.html delete mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/ot_font_loader.lua.html delete mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/package_path_searcher.lua.html create mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/fonts/TwitterColorEmoji-SVGinOT.ttf delete mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.0.0-1.rockspec create mode 100644 Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.1.0-1.rockspec create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/.gitattributes create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/.gitignore create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/.gitmodules create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/.travis.yml create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/CMakeLists.txt delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/Makefile.orig create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/README.md create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/azure-pipelines.yml create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/Makefile create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/environment.pickle create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-1.x.doctree create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-2.x.doctree create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi.doctree create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppcode.doctree create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/pplib.doctree create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppnew.doctree create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/.buildinfo create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-1.x.rst.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-2.x.rst.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi.rst.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppcode.rst.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/pplib.rst.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppnew.rst.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/ajax-loader.gif create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/background_b01.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/basic.css create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.css create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-bright.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-close.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries_src.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/doctools.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/documentation_options.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/down-pressed.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/down.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/file.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/jquery-3.2.1.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/jquery.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/language_data.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/minus.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/plus.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/pygments.css create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/searchtools.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/underscore-1.3.1.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/underscore.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/up-pressed.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/up.png create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/websupport.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/genindex.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/objects.inv create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/ppapi-1.x.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/ppapi-2.x.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/ppapi.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/ppcode.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/pplib.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/ppnew.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/search.html create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/searchindex.js create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/conf.py create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/make.bat create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/ppapi-1.x.rst create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/ppapi-2.x.rst create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/ppcode.rst create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/pplib.rst create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/doc/ppnew.rst delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/.buildinfo delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_sources/ppapi.rst.txt delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_sources/ppcode.rst.txt delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_sources/pplib.rst.txt delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/ajax-loader.gif delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/background_b01.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/basic.css delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/bizstyle.css delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/bizstyle.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/comment-bright.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/comment-close.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/comment.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/css3-mediaqueries.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/css3-mediaqueries_src.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/doctools.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/documentation_options.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/down-pressed.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/down.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/file.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/jquery-3.2.1.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/jquery.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/minus.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/plus.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/pygments.css delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/searchtools.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/underscore-1.3.1.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/underscore.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/up-pressed.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/up.png delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/_static/websupport.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/genindex.html delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/objects.inv delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/ppapi.html delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/ppcode.html delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/pplib.html delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/search.html delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/html/searchindex.js delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppapi.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/pparray.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/pparray.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppconf.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppcrypt.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppcrypt.c.orig delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppcrypt.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppdict.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppdict.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppfilter.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppheap.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppheap.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/pplib.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppload.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppload.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppstream.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppstream.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/pptest1.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/pptest2.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/pptest3.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppxref.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/ppxref.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/CMakeLists.txt create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/Makefile create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/Makefile.vc create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppapi.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/pparray.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/pparray.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppconf.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppcrypt.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppcrypt.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppdict.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppdict.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppfilter.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppheap.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppheap.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/pplib.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppload.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppload.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppstream.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppstream.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/pptest1.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/pptest2.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/pptest3.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppxref.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/ppxref.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/README.md create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilbasexx.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilbasexx.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilcrypt.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilcrypt.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilcryptdef.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utildecl.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilflate.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilflate.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilfpred.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilfpred.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utiliof.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utiliof.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utillog.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utillog.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utillzw.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utillzw.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmd5.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmd5.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmem.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmem.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmemallc.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmemallh.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmemheap.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmemheap.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmemheapiof.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmemheapiof.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmeminfo.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilmeminfo.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilnumber.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilnumber.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilplat.h create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilsha.c create mode 100644 Build/source/texk/web2c/luatexdir/luapplib/src/util/utilsha.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilarm.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilbasexx.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilbasexx.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilcrypt.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilcrypt.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilcryptdef.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utildecl.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilflate.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilflate.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilfpred.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilfpred.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utiliof.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utiliof.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utillog.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utillog.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utillzw.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utillzw.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilmd5.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilmd5.c.orig delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilmd5.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilmd5.h.orig delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilmem.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilmem.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilnumber.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilnumber.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilplat.h delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilsha.c delete mode 100644 Build/source/texk/web2c/luatexdir/luapplib/util/utilsha.h (limited to 'Build/source/texk') diff --git a/Build/source/texk/web2c/luatexdir/ChangeLog b/Build/source/texk/web2c/luatexdir/ChangeLog index 9f32ba3a1d4..33b871083ab 100644 --- a/Build/source/texk/web2c/luatexdir/ChangeLog +++ b/Build/source/texk/web2c/luatexdir/ChangeLog @@ -1,3 +1,42 @@ +2020-02-12 Luigi Scarso + * restore state for \input delimited with {} + + +2020-02-11 Luigi Scarso + * patches for -fno-common (thanks to D. Seifert of Gentoo team) + + +2020-01-25 Luigi Scarso + * sync with upstream pplib + * sync with upstream luaharfbuzz + + +2020-01-11 Luigi Scarso + * shape fix (HH) + +2020-01-03 Luigi Scarso + * luatex 1.12.0: updated to pplib 2.0 + +2020-01-02 Luigi Scarso + * better separation between luatex and luahbtex at build time + + +2019-12-31 Luigi Scarso + * scaled virtual font (HH) + + +2019-12-19 Luigi Scarso + * fixed inclusion of pdf files with a invalid pageDict (exit, don't load it) + + +2019-12-11 Luigi Scarso + * add catcode table check to set_macro (HH) + + +2019-12-05 Luigi Scarso + * two fixes for lua user nodes (error report of Sigitas Tolusis ) + + 2019-11-08 Luigi Scarso * record a few more files (in kpse enabled mode) (HH) * better recorder code in wrapped lua diff --git a/Build/source/texk/web2c/luatexdir/am/libluatex.am b/Build/source/texk/web2c/luatexdir/am/libluatex.am index 8302c311143..f3ba0d4f0ec 100644 --- a/Build/source/texk/web2c/luatexdir/am/libluatex.am +++ b/Build/source/texk/web2c/luatexdir/am/libluatex.am @@ -17,18 +17,14 @@ LUA_DEPEND = $(LUA53_DEPEND) ## EXTRA_LIBRARIES += libluatex.a libluajittex.a libluatexspecific.a libluajittexspecific.a libluahbtexspecific.a libluajithbtexspecific.a - -## it's not true that luatex depends on libluaharfbuzz.a -## but for the moment we keep it -## -libluatex_a_DEPENDENCIES = libff.a libluamisc.a libluaharfbuzz.a -libluajittex_a_DEPENDENCIES = libff.a libluajitmisc.a libluajitharfbuzz.a +libluatex_a_DEPENDENCIES = libff.a libluamisc.a +libluajittex_a_DEPENDENCIES = libff.a libluajitmisc.a libluatex_a_preflags = $(AM_CPPFLAGS) $(ZLIB_INCLUDES) $(LIBPNG_INCLUDES) $(HARFBUZZ_INCLUDES) libluatex_a_preflags += -I$(srcdir)/libmd5 libluatex_a_preflags += -DpdfTeX -I$(srcdir)/luatexdir libluatex_a_preflags += -I$(srcdir)/luatexdir/unilib -libluatex_a_preflags += -I$(srcdir)/luatexdir/luapplib/util +libluatex_a_preflags += -I$(srcdir)/luatexdir/luapplib/src/util libluatex_a_preflags += -I$(srcdir)/luatexdir/luafontloader/fontforge/inc libluatex_a_preflags += -DLUA_FF_LIB=1 -I$(srcdir)/luatexdir/luafontloader/fontforge/fontforge libluatex_a_preflags += -DSYNCTEX_ENGINE_H='' -I$(srcdir)/synctexdir diff --git a/Build/source/texk/web2c/luatexdir/am/luapplib.am b/Build/source/texk/web2c/luatexdir/am/luapplib.am index 06293da4ddd..7cca34c2049 100644 --- a/Build/source/texk/web2c/luatexdir/am/luapplib.am +++ b/Build/source/texk/web2c/luatexdir/am/luapplib.am @@ -18,13 +18,13 @@ $(libluajitpplib_a_OBJECTS): $(LUAJIT_DEPEND) libluapplib_a_CPPFLAGS = \ - -I$(top_srcdir)/luatexdir/luapplib -I$(top_srcdir)/luatexdir/luapplib/util $(ZLIB_INCLUDES) $(LUA_INCLUDES) + -I$(top_srcdir)/luatexdir/luapplib -I$(top_srcdir)/luatexdir/luapplib/src -I$(top_srcdir)/luatexdir/luapplib/src/util $(ZLIB_INCLUDES) $(LUA_INCLUDES) #liblua53pplib_a_CPPFLAGS = \ -# -I$(top_srcdir)/luatexdir/luapplib -I$(top_srcdir)/luatexdir/luapplib/util $(ZLIB_INCLUDES) $(LUA_LUA53_INCLUDES) +# -I$(top_srcdir)/luatexdir/luapplib -I$(top_srcdir)/luatexdir/luapplib/src -I$(top_srcdir)/luatexdir/luapplib/src/util $(ZLIB_INCLUDES) $(LUA_LUA53_INCLUDES) libluajitpplib_a_CPPFLAGS = \ - -I$(top_srcdir)/luatexdir/luapplib -I$(top_srcdir)/luatexdir/luapplib/util $(ZLIB_INCLUDES) $(LUAJIT_INCLUDES) + -I$(top_srcdir)/luatexdir/luapplib -I$(top_srcdir)/luatexdir/luapplib/src -I$(top_srcdir)/luatexdir/luapplib/src/util $(ZLIB_INCLUDES) $(LUAJIT_INCLUDES) libluapplib_a_CFLAGS = # $(WARNING_CFLAGS) libluajitpplib_a_CFLAGS = # $(WARNING_CFLAGS) @@ -34,53 +34,60 @@ nodist_libluapplib_a_SOURCES = $(libluapplib_sources) nodist_libluajitpplib_a_SOURCES = $(libluapplib_sources) libluapplib_sources = \ - luatexdir/luapplib/ppapi.h \ - luatexdir/luapplib/pparray.c \ - luatexdir/luapplib/pparray.h \ - luatexdir/luapplib/ppconf.h \ - luatexdir/luapplib/ppcrypt.c \ - luatexdir/luapplib/ppcrypt.h \ - luatexdir/luapplib/ppdict.c \ - luatexdir/luapplib/ppdict.h \ - luatexdir/luapplib/ppfilter.h \ - luatexdir/luapplib/ppheap.c \ - luatexdir/luapplib/ppheap.h \ - luatexdir/luapplib/pplib.h \ - luatexdir/luapplib/ppload.c \ - luatexdir/luapplib/ppload.h \ - luatexdir/luapplib/ppstream.c \ - luatexdir/luapplib/ppstream.h \ - luatexdir/luapplib/pptest1.c \ - luatexdir/luapplib/pptest2.c \ - luatexdir/luapplib/pptest3.c \ - luatexdir/luapplib/ppxref.c \ - luatexdir/luapplib/ppxref.h \ - luatexdir/luapplib/util/utilarm.h \ - luatexdir/luapplib/util/utilbasexx.c \ - luatexdir/luapplib/util/utilbasexx.h \ - luatexdir/luapplib/util/utilcrypt.c \ - luatexdir/luapplib/util/utilcrypt.h \ - luatexdir/luapplib/util/utilcryptdef.h \ - luatexdir/luapplib/util/utildecl.h \ - luatexdir/luapplib/util/utilflate.c \ - luatexdir/luapplib/util/utilflate.h \ - luatexdir/luapplib/util/utilfpred.c \ - luatexdir/luapplib/util/utilfpred.h \ - luatexdir/luapplib/util/utiliof.c \ - luatexdir/luapplib/util/utiliof.h \ - luatexdir/luapplib/util/utillog.c \ - luatexdir/luapplib/util/utillog.h \ - luatexdir/luapplib/util/utillzw.c \ - luatexdir/luapplib/util/utillzw.h \ - luatexdir/luapplib/util/utilmd5.c \ - luatexdir/luapplib/util/utilmd5.h \ - luatexdir/luapplib/util/utilmem.c \ - luatexdir/luapplib/util/utilmem.h \ - luatexdir/luapplib/util/utilnumber.c \ - luatexdir/luapplib/util/utilnumber.h \ - luatexdir/luapplib/util/utilplat.h \ - luatexdir/luapplib/util/utilsha.c \ - luatexdir/luapplib/util/utilsha.h + luatexdir/luapplib/src/ppapi.h \ + luatexdir/luapplib/src/pparray.c \ + luatexdir/luapplib/src/pparray.h \ + luatexdir/luapplib/src/ppconf.h \ + luatexdir/luapplib/src/ppcrypt.c \ + luatexdir/luapplib/src/ppcrypt.h \ + luatexdir/luapplib/src/ppdict.c \ + luatexdir/luapplib/src/ppdict.h \ + luatexdir/luapplib/src/ppfilter.h \ + luatexdir/luapplib/src/ppheap.c \ + luatexdir/luapplib/src/ppheap.h \ + luatexdir/luapplib/src/pplib.h \ + luatexdir/luapplib/src/ppload.c \ + luatexdir/luapplib/src/ppload.h \ + luatexdir/luapplib/src/ppstream.c \ + luatexdir/luapplib/src/ppstream.h \ + luatexdir/luapplib/src/pptest1.c \ + luatexdir/luapplib/src/pptest2.c \ + luatexdir/luapplib/src/pptest3.c \ + luatexdir/luapplib/src/ppxref.c \ + luatexdir/luapplib/src/ppxref.h \ + luatexdir/luapplib/src/util/utilbasexx.c \ + luatexdir/luapplib/src/util/utilbasexx.h \ + luatexdir/luapplib/src/util/utilcrypt.c \ + luatexdir/luapplib/src/util/utilcrypt.h \ + luatexdir/luapplib/src/util/utilcryptdef.h \ + luatexdir/luapplib/src/util/utildecl.h \ + luatexdir/luapplib/src/util/utilflate.c \ + luatexdir/luapplib/src/util/utilflate.h \ + luatexdir/luapplib/src/util/utilfpred.c \ + luatexdir/luapplib/src/util/utilfpred.h \ + luatexdir/luapplib/src/util/utiliof.c \ + luatexdir/luapplib/src/util/utiliof.h \ + luatexdir/luapplib/src/util/utillog.c \ + luatexdir/luapplib/src/util/utillog.h \ + luatexdir/luapplib/src/util/utillzw.c \ + luatexdir/luapplib/src/util/utillzw.h \ + luatexdir/luapplib/src/util/utilmd5.c \ + luatexdir/luapplib/src/util/utilmd5.h \ + luatexdir/luapplib/src/util/utilmem.c \ + luatexdir/luapplib/src/util/utilmem.h \ + luatexdir/luapplib/src/util/utilmemallc.h \ + luatexdir/luapplib/src/util/utilmemallh.h \ + luatexdir/luapplib/src/util/utilmemheap.c \ + luatexdir/luapplib/src/util/utilmemheap.h \ + luatexdir/luapplib/src/util/utilmemheapiof.c \ + luatexdir/luapplib/src/util/utilmemheapiof.h \ + luatexdir/luapplib/src/util/utilmeminfo.c \ + luatexdir/luapplib/src/util/utilmeminfo.h \ + luatexdir/luapplib/src/util/utilnumber.c \ + luatexdir/luapplib/src/util/utilnumber.h \ + luatexdir/luapplib/src/util/utilplat.h \ + luatexdir/luapplib/src/util/utilsha.c \ + luatexdir/luapplib/src/util/utilsha.h #liblua53pplib_sources = $(libluapplib_sources) diff --git a/Build/source/texk/web2c/luatexdir/am/luatex.am b/Build/source/texk/web2c/luatexdir/am/luatex.am index 9643a7ec8be..ab48c047c06 100644 --- a/Build/source/texk/web2c/luatexdir/am/luatex.am +++ b/Build/source/texk/web2c/luatexdir/am/luatex.am @@ -113,8 +113,8 @@ luatex_DEPENDENCIES = $(luatex_depend) libluatex.a libluatexspecific.a luajittex_DEPENDENCIES = $(luatex_depend) libluajittex.a libluajittexspecific.a luahbtex_depend = $(proglib) $(KPATHSEA_DEPEND) $(LIBPNG_DEPEND) libmputil.a libmd5.a -luahbtex_DEPENDENCIES = $(luahbtex_depend) libluatex.a libluahbtexspecific.a -luajithbtex_DEPENDENCIES = $(luatex_depend) libluajittex.a libluajithbtexspecific.a +luahbtex_DEPENDENCIES = $(luahbtex_depend) libluatex.a libluahbtexspecific.a libluaharfbuzz.a +luajithbtex_DEPENDENCIES = $(luatex_depend) libluajittex.a libluajithbtexspecific.a libluajitharfbuzz.a diff --git a/Build/source/texk/web2c/luatexdir/font/luafont.c b/Build/source/texk/web2c/luatexdir/font/luafont.c index 14efbf8a794..dd0c6856495 100644 --- a/Build/source/texk/web2c/luatexdir/font/luafont.c +++ b/Build/source/texk/web2c/luatexdir/font/luafont.c @@ -169,6 +169,207 @@ static void dump_math_kerns(lua_State * L, charinfo * co, int l, int id) } } +#define set_packet_number(fw) { \ + fw = *(vfp++); \ + fw = fw * 256 + *(vfp++); \ + fw = fw * 256 + *(vfp++); \ + fw = fw * 256 + *(vfp++); \ +} + +#define set_packet_scaled(fw) { \ + fw = *(vfp++); \ + if (fw > 127) { \ + fw = fw - 256; \ + } \ + fw = fw * 256 + *(vfp++); \ + fw = fw * 256 + *(vfp++); \ + fw = fw * 256 + *(vfp++); \ +} + +static void font_commands_to_lua(lua_State * L, internal_font_number f, charinfo * co) +{ + eight_bits *vfp = get_charinfo_packets(co); + if (vfp != NULL) { + int cmd; + int i = 1; + lua_push_string_by_name(L,commands); + lua_newtable(L); + while ((cmd = *(vfp++)) != packet_end_code) { + switch (cmd) { + case packet_font_code: + { + halfword f ; + set_packet_number(f); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,font); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, f); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_push_code: + { + lua_createtable(L, 1, 0); + lua_push_string_by_name(L,push); + lua_rawseti(L, -2, 1); + lua_rawseti(L, -2, i++); + } + break; + case packet_pop_code: + { + lua_createtable(L, 1, 0); + lua_push_string_by_name(L,pop); + lua_rawseti(L, -2, 1); + lua_rawseti(L, -2, i++); + } + break; + case packet_char_code: + { + halfword c ; + set_packet_number(c); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,char); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, c); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_rule_code: + { + halfword h, w ; + set_packet_scaled(h); + set_packet_scaled(w); + lua_createtable(L, 3, 0); + lua_push_string_by_name(L,rule); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, h); + lua_rawseti(L, -2, 2); + lua_pushinteger(L, w); + lua_rawseti(L, -2, 3); + lua_rawseti(L, -2, i++); + } + break; + case packet_right_code: + { + halfword r ; + set_packet_scaled(r); + lua_createtable(L, 1, 0); + lua_push_string_by_name(L,right); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, r); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_down_code: + { + halfword d ; + set_packet_scaled(d); + lua_createtable(L, 1, 0); + lua_push_string_by_name(L,down); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, d); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_pdf_code: + { + halfword m, l; + set_packet_number(m); + set_packet_number(l); + lua_createtable(L, 3, 0); + lua_push_string_by_name(L,pdf); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, m); + lua_rawseti(L, -2, 2); + lua_pushstring(L,""); + lua_rawseti(L, -2, 3); + lua_rawseti(L, -2, i++); + vfp += l; + } + break; + case packet_pdf_mode: + { + halfword m; + set_packet_number(m); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,mode); + lua_rawseti(L, -2, 1); + lua_pushinteger(L, m); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_special_code: + { + halfword l; + set_packet_number(l); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,special); + lua_rawseti(L, -2, 1); + lua_pushstring(L,""); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + vfp += l; + } + break; + case packet_lua_code: + { + halfword n; + set_packet_number(n); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,lua); + lua_rawseti(L, -2, 1); + lua_pushstring(L,""); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_image_code: + { + halfword n; + set_packet_number(n); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,image); + lua_rawseti(L, -2, 1); + lua_pushstring(L,""); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_node_code: + { + halfword n; + set_packet_number(n); + lua_createtable(L, 2, 0); + lua_push_string_by_name(L,node); + lua_rawseti(L, -2, 1); + lua_pushstring(L,""); + lua_rawseti(L, -2, 2); + lua_rawseti(L, -2, i++); + } + break; + case packet_nop_code: + { + lua_createtable(L, 1, 0); + lua_push_string_by_name(L,nop); + lua_rawseti(L, -2, 1); + lua_rawseti(L, -2, i++); + } + break; + case packet_scale_code: + break; + default: + break; + } + } + lua_rawset(L, -3); + } +} + static void font_char_to_lua(lua_State * L, internal_font_number f, charinfo * co) { liginfo *l; @@ -343,6 +544,7 @@ static void font_char_to_lua(lua_State * L, internal_font_number f, charinfo * c else lua_pop(L, 2); } + font_commands_to_lua(L,f,co); } static void write_lua_parameters(lua_State * L, int f) @@ -432,11 +634,11 @@ static void write_lua_math_parameters(lua_State * L, int f) lua_rawset(L, -3); } -int font_to_lua(lua_State * L, int f) +int font_to_lua(lua_State * L, int f, int usecache) { int k; charinfo *co; - if (font_cache_id(f) > 0) { + if (usecache && font_cache_id(f) > 0) { /*tex Fetch the table from the registry if it was saved there by |font_from_lua|. */ lua_rawgeti(L, LUA_REGISTRYINDEX, font_cache_id(f)); return 1; @@ -523,13 +725,6 @@ int font_to_lua(lua_State * L, int f) } } lua_rawset(L, -3); - if (font_cache_id(f) == 0) { - /*tex Renew the cache. */ - int r; - lua_pushvalue(L, -1); - r = luaL_ref(L, LUA_REGISTRYINDEX); - set_font_cache_id(f, r); - } return 1; } diff --git a/Build/source/texk/web2c/luatexdir/font/luatexfont.h b/Build/source/texk/web2c/luatexdir/font/luatexfont.h index cd199417313..5eb6a5bd94e 100644 --- a/Build/source/texk/web2c/luatexdir/font/luatexfont.h +++ b/Build/source/texk/web2c/luatexdir/font/luatexfont.h @@ -128,8 +128,8 @@ int write_tounicode(PDF, char **, char *); void replace_packet_fonts(internal_font_number f, int *old_fontid, int *new_fontid, int count); int *packet_local_fonts(internal_font_number f, int *num); -int packet_cur_s; /* current |do_vf_packet()| recursion level */ -int packet_stack_ptr; /* pointer into |packet_stack| */ +extern int packet_cur_s; /* current |do_vf_packet()| recursion level */ +extern int packet_stack_ptr; /* pointer into |packet_stack| */ vf_struct *new_vfstruct(void); /* writecff.c */ diff --git a/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-luatex.c b/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-luatex.c new file mode 100644 index 00000000000..58a4e7caabf --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-luatex.c @@ -0,0 +1,106 @@ +static void set_glyph_unicode(char *s, glyph_unicode_entry * gp) +{ + char buf[SMALL_BUF_SIZE], buf2[SMALL_BUF_SIZE], *p; + long code; + boolean last_component; + glyph_unicode_entry tmp, *ptmp; + /*tex Skip dummy entries. */ + if (s == NULL || s == notdef) + return; + /*tex Strip everything after the first dot. */ + p = strchr(s, '.'); + if (p != NULL) { + *buf = 0; + strncat(buf, s, (size_t) (p - s)); + s = buf; + } + if (strlen(s) == 0) + return; + /*tex Check for case of multiple components separated by |_|. */ + p = strchr(s, '_'); + if (p != NULL) { + assert(strlen(s) < sizeof(buf)); + if (s != buf) { + strcpy(buf, s); + p = strchr(buf, '_'); + s = buf; + } + *buf2 = 0; + last_component = false; + for (;;) { + *p = 0; + tmp.code = UNI_UNDEF; + set_glyph_unicode(s, &tmp); + switch (tmp.code) { + case UNI_UNDEF: + /*tex Not found, do nothing. */ + break; + case UNI_STRING: + /*tex |s| matched an entry with string value in the database. */ + assert(tmp.unicode_seq != NULL); + assert(strlen(buf2) + strlen(tmp.unicode_seq) < sizeof(buf2)); + strcat(buf2, tmp.unicode_seq); + break; + case UNI_EXTRA_STRING: + /*tex |s| is a multiple value of form "uniXXXX" */ + assert(strlen(buf2) + strlen(tmp.unicode_seq) < sizeof(buf2)); + strcat(buf2, tmp.unicode_seq); + xfree(tmp.unicode_seq); + break; + default: + /*tex + |s| matched an entry with numeric value in the database, or a + value derived from |uXXXX|. + */ + assert(tmp.code >= 0); + strcat(buf2, utf16be_str(tmp.code)); + } + if (last_component) + break; + s = p + 1; + p = strchr(s, '_'); + if (p == NULL) { + p = strend(s); + last_component = true; + } + } + gp->code = UNI_EXTRA_STRING; + gp->unicode_seq = xstrdup(buf2); + return; + } + /*tex Lookup glyph name in the database. */ + tmp.name = s; + tmp.code = UNI_UNDEF; + ptmp = (glyph_unicode_entry *) avl_find(glyph_unicode_tree, &tmp); + if (ptmp != NULL) { + gp->code = ptmp->code; + gp->unicode_seq = ptmp->unicode_seq; + return; + } + /*tex Check for case of |uniXXXX|, multiple 4-hex-digit values allowed. */ + if (str_prefix(s, "uni")) { + p = s + strlen("uni"); + code = check_unicode_value(p, true); + if (code != UNI_UNDEF) { + if (strlen(p) == 4) { + /*tex Single value: */ + gp->code = code; + } else { + /*tex Multiple value: */ + gp->code = UNI_EXTRA_STRING; + gp->unicode_seq = xstrdup(p); + } + } + /*tex Since the last case cannot happen: */ + return; + } + /*tex Check for case of |uXXXX|, a single value up to 6 hex digits. */ + if (str_prefix(s, "u")) { + p = s + strlen("u"); + code = check_unicode_value(p, false); + if (code != UNI_UNDEF) { + assert(code >= 0); + gp->code = code; + } + } +} diff --git a/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-pdftex.c b/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-pdftex.c new file mode 100644 index 00000000000..b89a770e078 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-pdftex.c @@ -0,0 +1,126 @@ +static void set_glyph_unicode(const char *s, const char* tfmname, + glyph_unicode_entry *gp) +{ + char buf[SMALL_BUF_SIZE], buf2[SMALL_BUF_SIZE], *p; + const char *p2; /* p2 points in s; p above points in writable copies */ + long code; + boolean last_component; + glyph_unicode_entry tmp, *ptmp; + /*tex Skip dummy entries. */ + if (s == NULL || s == notdef) + return; + /*tex Strip everything after the first dot. */ + p = strchr(s, '.'); + if (p != NULL) { + *buf = 0; + strncat(buf, s, p - s); + s = buf; + } + if (strlen(s) == 0) + return; + /*tex Check for case of multiple components separated by |_|. */ + p = strchr(s, '_'); + if (p != NULL) { + assert(strlen(s) < sizeof(buf)); + if (s != buf) { + strcpy(buf, s); + p = strchr(buf, '_'); + s = buf; + } + *buf2 = 0; + last_component = false; + for (;;) { + *p = 0; + tmp.code = UNI_UNDEF; + set_glyph_unicode(s, tfmname, &tmp); + switch (tmp.code) { + case UNI_UNDEF: + /*tex Not found, do nothing. */ + break; + case UNI_STRING: + /*tex |s| matched an entry with string value in the database. */ + assert(tmp.unicode_seq != NULL); + assert(strlen(buf2) + strlen(tmp.unicode_seq) < sizeof(buf2)); + strcat(buf2, tmp.unicode_seq); + break; + case UNI_EXTRA_STRING: + /*tex |s| is a multiple value of form "uniXXXX" */ + assert(strlen(buf2) + strlen(tmp.unicode_seq) < sizeof(buf2)); + strcat(buf2, tmp.unicode_seq); + xfree(tmp.unicode_seq); + break; + default: + /*tex + |s| matched an entry with numeric value in the database, or a + value derived from |uXXXX|. + */ + assert(tmp.code >= 0); + strcat(buf2, utf16be_str(tmp.code)); + } + if (last_component) + break; + s = p + 1; + p = strchr(s, '_'); + if (p == NULL) { + p = strend(s); + last_component = true; + } + } + gp->code = UNI_EXTRA_STRING; + gp->unicode_seq = xstrdup(buf2); + return; + } + + /* Glyph name search strategy: first look up the glyph name in the + tfm's namespace, failing that look it up in the main database. */ + /* Note: buf may alias s in the code below, but s and buf2 are + guaranteed to be distinct because the code changing buf2 above + always returns before reaching the code below. */ + + /* lookup for glyph name in the tfm's namespace */ + snprintf(buf2, SMALL_BUF_SIZE, "tfm:%s/%s", tfmname, s); + tmp.name = buf2; + tmp.code = UNI_UNDEF; + ptmp = (glyph_unicode_entry *) avl_find(glyph_unicode_tree, &tmp); + if (ptmp != NULL) { + gp->code = ptmp->code; + gp->unicode_seq = ptmp->unicode_seq; + return; + } + + /* lookup for glyph name in the main database */ + snprintf(buf2, SMALL_BUF_SIZE, "%s", s); + tmp.name = buf2; + tmp.code = UNI_UNDEF; + ptmp = (glyph_unicode_entry *) avl_find(glyph_unicode_tree, &tmp); + if (ptmp != NULL) { + gp->code = ptmp->code; + gp->unicode_seq = ptmp->unicode_seq; + return; + } + + /*tex Check for case of |uniXXXX|, multiple 4-hex-digit values allowed. */ + if (str_prefix(s, "uni")) { + p2 = s + strlen("uni"); + code = check_unicode_value(p2, true); + if (code != UNI_UNDEF) { + if (strlen(p2) == 4) /* single value */ + gp->code = code; + else { /* multiple value */ + gp->code = UNI_EXTRA_STRING; + gp->unicode_seq = xstrdup(p2); + } + } + /*tex Since the last case cannot happen: */ + return; + } + /*tex Check for case of |uXXXX|, a single value up to 6 hex digits. */ + if (str_prefix(s, "u")) { + p2 = s + strlen("u"); + code = check_unicode_value(p2, false); + if (code != UNI_UNDEF) { + assert(code >= 0); + gp->code = code; + } + } +} diff --git a/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-readme.txt b/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-readme.txt new file mode 100644 index 00000000000..947495ae000 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/font/pdfglyphtounicode-readme.txt @@ -0,0 +1,10 @@ +In pdftex there is are some more heuristics going on when determining the +tounicode mapping: + +- more lookups using periods +- a prefix tfm:cmr10/foo -> bar mapping + +Because in luatex one can have a callback that just loads the tfm and then +decorates it with tounicodes we don't do this in luatex. + +HH diff --git a/Build/source/texk/web2c/luatexdir/font/texfont.h b/Build/source/texk/web2c/luatexdir/font/texfont.h index 7c27d09565c..7b07bffa7d7 100644 --- a/Build/source/texk/web2c/luatexdir/font/texfont.h +++ b/Build/source/texk/web2c/luatexdir/font/texfont.h @@ -329,7 +329,6 @@ boolean cmp_font_area(int, str_number); # define font_streamprovider(a) font_tables[a]->_font_streamprovider # define set_font_streamprovider(a,b) font_streamprovider(a) = b - # define font_oldmath(a) font_tables[a]->_font_oldmath # define set_font_oldmath(a,b) font_oldmath(a) = b diff --git a/Build/source/texk/web2c/luatexdir/font/vfpacket.c b/Build/source/texk/web2c/luatexdir/font/vfpacket.c index 41132c54a6d..ab90eca5eea 100644 --- a/Build/source/texk/web2c/luatexdir/font/vfpacket.c +++ b/Build/source/texk/web2c/luatexdir/font/vfpacket.c @@ -29,6 +29,9 @@ with LuaTeX; if not, see . */ +int packet_cur_s; +int packet_stack_ptr; + #define packet_number(fw) { \ fw = *(vfp++); \ fw = fw * 256 + *(vfp++); \ diff --git a/Build/source/texk/web2c/luatexdir/image/epdf.h b/Build/source/texk/web2c/luatexdir/image/epdf.h index fa66eeb4d23..e002b0b5c7c 100644 --- a/Build/source/texk/web2c/luatexdir/image/epdf.h +++ b/Build/source/texk/web2c/luatexdir/image/epdf.h @@ -70,7 +70,8 @@ typedef enum { FE_FAIL, FE_RETURN_NULL } file_error_mode; # include "lua.h" # include "lauxlib.h" -# include "luapplib/pplib.h" +# include "luapplib/src/pplib.h" + /* pdfgen.w */ diff --git a/Build/source/texk/web2c/luatexdir/image/pdftoepdf.c b/Build/source/texk/web2c/luatexdir/image/pdftoepdf.c index 547d0f67cac..a43f1dac4cc 100644 --- a/Build/source/texk/web2c/luatexdir/image/pdftoepdf.c +++ b/Build/source/texk/web2c/luatexdir/image/pdftoepdf.c @@ -187,6 +187,9 @@ PdfDocument *refPdfDocument(const char *file_path, file_error_mode fe, const cha } } if (pdfe != NULL) { + if (ppdoc_crypt_status(pdfe) < 0 && userpassword==NULL) { + formatted_error("pdf inclusion","the pdf file '%s' is encrypted, passwords wrong",file_path); + } if (ppdoc_crypt_status(pdfe) < 0) { ppdoc_crypt_pass(pdfe,userpassword,strlen(userpassword),NULL,0); } @@ -250,7 +253,7 @@ PdfDocument *refMemStreamPdfDocument(char *docstream, unsigned long long streams free(checksum); } if (pdf_doc->pdfe == NULL) { - pdfe = ppdoc_mem(docstream, streamsize); + pdfe = ppdoc_mem(docstream, (size_t) streamsize); pdf_doc->pc++; if (pdfe == NULL) { normal_error("pdf inclusion","reading pdf Stream failed"); @@ -367,24 +370,24 @@ static int addInObj(PDF pdf, PdfDocument * pdf_doc, ppref * ref) static void copyObject(PDF, PdfDocument *, ppobj *); -static void copyString(PDF pdf, ppstring str) +static void copyString(PDF pdf, ppstring *str) { pdf_check_space(pdf); - switch (ppstring_type((void *)(str))) { + switch (ppstring_type(str)) { case PPSTRING_PLAIN: pdf_out(pdf, '('); - pdf_out_block(pdf, (const char *) str, ppstring_size((void *)(str))); + pdf_out_block(pdf, ppstring_data(str), ppstring_size(str)); pdf_out(pdf, ')'); break; case PPSTRING_BASE16: pdf_out(pdf, '<'); - pdf_out_block(pdf, (const char *) str, ppstring_size((void *)(str))); + pdf_out_block(pdf, ppstring_data(str), ppstring_size(str)); pdf_out(pdf, '>'); break; case PPSTRING_BASE85: pdf_out(pdf, '<'); pdf_out(pdf, '~'); - pdf_out_block(pdf, (const char *) str, ppstring_size((void *)(str))); + pdf_out_block(pdf, ppstring_data(str), ppstring_size(str)); pdf_out(pdf, '~'); pdf_out(pdf, '>'); break; @@ -392,12 +395,10 @@ static void copyString(PDF pdf, ppstring str) pdf_set_space(pdf); } -/* static void copyName(PDF pdf, ppname *name) { - pdf_add_name(pdf, (const char *) name); + pdf_add_name(pdf, ppname_data(name)); } -*/ static void copyArray(PDF pdf, PdfDocument * pdf_doc, pparray * array) { @@ -416,7 +417,8 @@ static void copyDict(PDF pdf, PdfDocument * pdf_doc, ppdict *dict) int n = dict->size; pdf_begin_dict(pdf); for (i=0; iname),codecs[k]) == 0) { known = 1; break; } @@ -478,17 +479,17 @@ static void copyStream(PDF pdf, PdfDocument * pdf_doc, ppstream * stream) int i; pdf_begin_dict(pdf); for (i=0; isize; ++i) { - const char *key = ppdict_key(dict,i); + ppname *key = ppdict_key(dict,i); int copy = 1; int k; for (k = 0; ignoredkeys[k] != NULL; k++) { - if (strcmp(key,ignoredkeys[k]) == 0) { + if (strcmp(ppname_data(key),ignoredkeys[k]) == 0) { copy = 0; break; } } if (copy) { - pdf_add_name(pdf, key); + pdf_add_name(pdf, ppname_data(key)); copyObject(pdf, pdf_doc, ppdict_at(dict,i)); } } @@ -523,7 +524,7 @@ static void copyObject(PDF pdf, PdfDocument * pdf_doc, ppobj * obj) pdf_add_real(pdf,obj->number); /* ppobj_get_num_value(obj) */ break; case PPNAME: - pdf_add_name(pdf, (const char *) obj->name); /* ppobj_get_name(obj) */ + copyName(pdf, obj->name); break; case PPSTRING: copyString(pdf, obj->string); /* ppobj_get_string(obj) */ @@ -690,6 +691,9 @@ void read_pdf_info(image_dict * idict) get the required page */ pageDict = get_pdf_page_dict(pdfe,img_pagenum(idict)); + if (pageDict==NULL) { + formatted_error("pdf inclusion","unable to retrive dictionary for page '%i'",(int) img_pagenum(idict)); + } /* get the pagebox coordinates (media, crop,...) to use */ @@ -802,6 +806,9 @@ void write_epdf(PDF pdf, image_dict * idict, int suppress_optional_info) } pdfe = pdf_doc->pdfe; pageDict = get_pdf_page_dict(pdfe,img_pagenum(idict)); + if (pageDict==NULL) { + formatted_error("pdf inclusion","unable to retrive dictionary for page '%i'",(int) img_pagenum(idict)); + } /* write the Page header */ diff --git a/Build/source/texk/web2c/luatexdir/image/writeimg.h b/Build/source/texk/web2c/luatexdir/image/writeimg.h index dc86648e217..96771decd35 100644 --- a/Build/source/texk/web2c/luatexdir/image/writeimg.h +++ b/Build/source/texk/web2c/luatexdir/image/writeimg.h @@ -26,7 +26,7 @@ # include "pdf/pdfpage.h" typedef image_dict *idict_entry; -idict_entry *idict_array; +extern idict_entry *idict_array; void new_img_pdfstream_struct(image_dict *); image *new_image(void); diff --git a/Build/source/texk/web2c/luatexdir/lua/lcallbacklib.c b/Build/source/texk/web2c/luatexdir/lua/lcallbacklib.c index 5654bc71410..4e0defd1059 100644 --- a/Build/source/texk/web2c/luatexdir/lua/lcallbacklib.c +++ b/Build/source/texk/web2c/luatexdir/lua/lcallbacklib.c @@ -84,6 +84,7 @@ static const char *const callbacknames[] = { "page_order_index", "make_extensible", "process_pdf_image_content", + "provide_charproc_data", NULL }; @@ -195,6 +196,7 @@ void get_saved_lua_string(int r, const char *name, char **target) #define CALLBACK_BOOLEAN 'b' #define CALLBACK_INTEGER 'd' +#define CALLBACK_FLOAT 'f' #define CALLBACK_LINE 'l' #define CALLBACK_STRNUMBER 's' #define CALLBACK_STRING 'S' @@ -302,6 +304,9 @@ int do_run_callback(int special, const char *values, va_list vl) case CALLBACK_INTEGER: /* int */ lua_pushinteger(Luas, va_arg(vl, int)); break; + case CALLBACK_FLOAT: /* double */ + lua_pushnumber(Luas, va_arg(vl, double)); + break; case CALLBACK_STRNUMBER: /* TeX string */ s = makeclstring(va_arg(vl, int), &len); lua_pushlstring(Luas, s, len); @@ -361,6 +366,7 @@ int do_run_callback(int special, const char *values, va_list vl) nres = -nres; while (*values) { int b, t; + double d; halfword p; t = lua_type(Luas, nres); switch (*values++) { @@ -383,6 +389,14 @@ int do_run_callback(int special, const char *values, va_list vl) b = lua_tointeger(Luas, nres); *va_arg(vl, int *) = b; break; + case CALLBACK_FLOAT: + if (t != LUA_TNUMBER) { + fprintf(stderr, "callback should return a number, not: %s\n", lua_typename(Luas, t)); + goto EXIT; + } + d = lua_tonumber(Luas, nres); + *va_arg(vl, double *) = d; + break; case CALLBACK_LINE: /* TeX line ... happens frequently when we have a plug-in */ if (t == LUA_TNIL) { bufloc = 0; diff --git a/Build/source/texk/web2c/luatexdir/lua/lepdflib.cc.orig b/Build/source/texk/web2c/luatexdir/lua/lepdflib.cc.orig new file mode 100644 index 00000000000..ec5c90e8e00 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/lua/lepdflib.cc.orig @@ -0,0 +1,2939 @@ +/* lepdflib.cc + + Copyright 2009-2015 Taco Hoekwater + Copyright 2009-2013 Hartmut Henkel + + This file is part of LuaTeX. + + LuaTeX is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License as published by the Free + Software Foundation; either version 2 of the License, or (at your + option) any later version. + + LuaTeX is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public + License for more details. + + You should have received a copy of the GNU General Public License along + with LuaTeX; if not, see . */ + + +#include "image/epdf.h" + +/* + Patches for the new poppler 0.59 from: + + https://www.mail-archive.com/arch-commits@archlinux.org/msg357548.html + + with some modifications to comply the poppler API. +*/ + +/* define DEBUG */ + +/* objects allocated by poppler may not be deleted in the lepdflib */ + +typedef enum { ALLOC_POPPLER, ALLOC_LEPDF } alloctype; + +typedef struct { + void *d; + alloctype atype; // was it allocated by poppler or the lepdflib.cc? + PdfDocument *pd; // reference to PdfDocument, or NULL + unsigned long pc; // counter to detect PDFDoc change +} udstruct; + +static const char *ErrorCodeNames[] = { + "None", "OpenFile", "BadCatalog", + "Damaged", "Encrypted", "HighlightFile", "BadPrinter", "Printing", + "Permission", "BadPageNum", "FileIO", + NULL +}; + +#define M_Annot "epdf.Annot" /* ls-hh: epdf.* gives better protection in registry */ +#define M_Annots "epdf.Annots" +#define M_Array "epdf.Array" +#define M_Catalog "epdf.Catalog" +#define M_Dict "epdf.Dict" +#define M_EmbFile "epdf.EmbFile" +#define M_FileSpec "epdf.FileSpec" +#define M_GooString "epdf.GooString" +#define M_LinkDest "epdf.LinkDest" +#define M_Link "epdf.Link" +#define M_Links "epdf.Links" +#define M_Object "epdf.Object" +#define M_Page "epdf.Page" +#define M_PDFDoc "epdf.PDFDoc" +#define M_PDFRectangle "epdf.PDFRectangle" +#define M_Ref "epdf.Ref" +#define M_Stream "epdf.Stream" +#define M_StructElement "epdf.StructElement" +#define M_Attribute "epdf.Attribute" +#define M_TextSpan "epdf.TextSpan" +#define M_StructTreeRoot "epdf.StructTreeRoot" +#define M_XRefEntry "epdf.XRefEntry" +#define M_XRef "epdf.XRef" + +#define new_poppler_userdata(type) \ +static udstruct *new_##type##_userdata(lua_State * L) \ +{ \ + udstruct *a; \ + a = (udstruct *) lua_newuserdata(L, sizeof(udstruct)); /* udstruct ... */ \ + a->atype = ALLOC_POPPLER; \ + luaL_getmetatable(L, M_##type); /* m udstruct ... */ \ + lua_setmetatable(L, -2); /* udstruct ... */ \ + return a; \ +} + +new_poppler_userdata(PDFDoc); +new_poppler_userdata(Annot); +new_poppler_userdata(Array); +new_poppler_userdata(Catalog); +new_poppler_userdata(Dict); +new_poppler_userdata(EmbFile); +new_poppler_userdata(FileSpec); +new_poppler_userdata(LinkDest); +new_poppler_userdata(Links); +new_poppler_userdata(Object); +new_poppler_userdata(Page); +new_poppler_userdata(PDFRectangle); +new_poppler_userdata(Ref); +new_poppler_userdata(Stream); +new_poppler_userdata(StructElement); +new_poppler_userdata(Attribute); +new_poppler_userdata(TextSpan); +new_poppler_userdata(StructTreeRoot); +new_poppler_userdata(XRef); + +/* These two can go away as we don't change the document. */ + +static void pdfdoc_changed_error(lua_State * L) +{ + luaL_error(L, "PDFDoc changed or gone"); +} + +static void pdfdoc_differs_error(lua_State * L) +{ + luaL_error(L, "PDFDoc differs between arguments"); +} + +static int l_open_PDFDoc(lua_State * L) +{ + const char *file_path; + udstruct *uout; + PdfDocument *d; + file_path = luaL_checkstring(L, 1); // path + d = refPdfDocument(file_path, FE_RETURN_NULL); + if (d == NULL) + lua_pushnil(L); + else { + if (!(globalParams)) // globalParams could be already created + globalParams = new GlobalParams(); + uout = new_PDFDoc_userdata(L); + uout->d = d; + uout->atype = ALLOC_LEPDF; + uout->pc = d->pc; + uout->pd = d; + } + return 1; +} + +static int l_open_MemStreamPDFDoc(lua_State * L) +{ + const char *docstream = NULL; + char *docstream_usr = NULL ; + const char *file_id; + unsigned long long stream_size; + udstruct *uout; + PdfDocument *d; + switch (lua_type(L, 1)) { + case LUA_TSTRING: + docstream = luaL_checkstring(L, 1); // stream as Lua string + break; + case LUA_TLIGHTUSERDATA: + docstream = (const char *) lua_touserdata(L, 1); // stream as sequence of bytes + break; + default: + luaL_error(L, "bad argument: string or lightuserdata expected"); + } + if (docstream==NULL) + luaL_error(L, "bad document"); + stream_size = (unsigned long long) luaL_checkint(L, 2);// size of the stream + file_id = luaL_checkstring(L, 3); // a symbolic name for this stream, mandatory + if (file_id == NULL) + luaL_error(L, "PDFDoc has an invalid id"); + if (strlen(file_id) >STREAM_FILE_ID_LEN ) // a limit to the length of the string + luaL_error(L, "PDFDoc has a too long id"); + docstream_usr = (char *)gmalloc((unsigned) (stream_size + 1)); + if (!docstream_usr) + luaL_error(L, "no room for PDFDoc"); + memcpy(docstream_usr, docstream, (stream_size + 1)); + docstream_usr[stream_size]='\0'; + d = refMemStreamPdfDocument(docstream_usr, stream_size, file_id); + if (d == NULL) { + lua_pushnil(L); + lua_pushnil(L); + lua_pushnil(L); + } else if (d->file_path == NULL ) { + lua_pushnil(L); + lua_pushnil(L); + lua_pushnil(L); + } + else { + if (!(globalParams)) // globalParams could be already created + globalParams = new GlobalParams(); + uout = new_PDFDoc_userdata(L); + uout->d = d; + uout->atype = ALLOC_LEPDF; + uout->pc = d->pc; + uout->pd = d; + lua_pushstring(L,d->file_path); + lua_pushstring(L,STREAM_URI); + } + return 3; // stream, stream_id, stream_uri +} + +#define ATTRIBUTE_TYPE_ENTRY(name) \ + lua_pushstring(L, #name); \ + lua_pushinteger(L, Attribute::name); \ + lua_settable(L,-3) + + +#define OBJECT_TYPE(name) \ + lua_pushstring(L, #name); \ + lua_pushinteger(L, (int)name); \ + lua_settable(L,-3) + + +#define STRUCTELEMENT_TYPE_ENTRY(name) \ + lua_pushstring(L, #name); \ + lua_pushinteger(L, StructElement::name); \ + lua_settable(L,-3) + + +static int l_Attribute_Type(lua_State * L) { + lua_createtable (L, 0, 42); + ATTRIBUTE_TYPE_ENTRY(BBox); + ATTRIBUTE_TYPE_ENTRY(BackgroundColor); + ATTRIBUTE_TYPE_ENTRY(BorderColor); + ATTRIBUTE_TYPE_ENTRY(BorderThickness); + ATTRIBUTE_TYPE_ENTRY(Color); + ATTRIBUTE_TYPE_ENTRY(ColumnGap); + ATTRIBUTE_TYPE_ENTRY(ColumnWidths); + ATTRIBUTE_TYPE_ENTRY(Desc); + ATTRIBUTE_TYPE_ENTRY(Role); + ATTRIBUTE_TYPE_ENTRY(TextDecorationColor); + ATTRIBUTE_TYPE_ENTRY(TextDecorationThickness); + ATTRIBUTE_TYPE_ENTRY(BaselineShift); + ATTRIBUTE_TYPE_ENTRY(BlockAlign); + ATTRIBUTE_TYPE_ENTRY(BorderStyle); + ATTRIBUTE_TYPE_ENTRY(ColSpan); + ATTRIBUTE_TYPE_ENTRY(ColumnCount); + ATTRIBUTE_TYPE_ENTRY(EndIndent); + ATTRIBUTE_TYPE_ENTRY(GlyphOrientationVertical); + ATTRIBUTE_TYPE_ENTRY(Headers); + ATTRIBUTE_TYPE_ENTRY(Height); + ATTRIBUTE_TYPE_ENTRY(InlineAlign); + ATTRIBUTE_TYPE_ENTRY(LineHeight); + ATTRIBUTE_TYPE_ENTRY(ListNumbering); + ATTRIBUTE_TYPE_ENTRY(Padding); + ATTRIBUTE_TYPE_ENTRY(Placement); + ATTRIBUTE_TYPE_ENTRY(RowSpan); + ATTRIBUTE_TYPE_ENTRY(RubyAlign); + ATTRIBUTE_TYPE_ENTRY(RubyPosition); + ATTRIBUTE_TYPE_ENTRY(Scope); + ATTRIBUTE_TYPE_ENTRY(SpaceAfter); + ATTRIBUTE_TYPE_ENTRY(SpaceBefore); + ATTRIBUTE_TYPE_ENTRY(StartIndent); + ATTRIBUTE_TYPE_ENTRY(Summary); + ATTRIBUTE_TYPE_ENTRY(TBorderStyle); + ATTRIBUTE_TYPE_ENTRY(TPadding); + ATTRIBUTE_TYPE_ENTRY(TextAlign); + ATTRIBUTE_TYPE_ENTRY(TextDecorationType); + ATTRIBUTE_TYPE_ENTRY(TextIndent); + ATTRIBUTE_TYPE_ENTRY(Width); + ATTRIBUTE_TYPE_ENTRY(WritingMode); + ATTRIBUTE_TYPE_ENTRY(Unknown); + ATTRIBUTE_TYPE_ENTRY(checked); + return 1; +} + +static int l_Object_Type(lua_State * L) { + lua_createtable(L,0,16);/*nr of ObjType values*/ ; + OBJECT_TYPE(objBool); + OBJECT_TYPE(objInt); + OBJECT_TYPE(objReal); + OBJECT_TYPE(objString); + OBJECT_TYPE(objName); + OBJECT_TYPE(objNull); + OBJECT_TYPE(objArray); + OBJECT_TYPE(objDict); + OBJECT_TYPE(objStream); + OBJECT_TYPE(objRef); + OBJECT_TYPE(objCmd); + OBJECT_TYPE(objError); + OBJECT_TYPE(objEOF); + OBJECT_TYPE(objNone); + OBJECT_TYPE(objInt64); + OBJECT_TYPE(objDead); + return 1; +} + +static int l_StructElement_Type(lua_State * L) { + lua_createtable (L, 0, 50); + STRUCTELEMENT_TYPE_ENTRY(Document); + STRUCTELEMENT_TYPE_ENTRY(Part); + STRUCTELEMENT_TYPE_ENTRY(Art); + STRUCTELEMENT_TYPE_ENTRY(Sect); + STRUCTELEMENT_TYPE_ENTRY(Div); + STRUCTELEMENT_TYPE_ENTRY(BlockQuote); + STRUCTELEMENT_TYPE_ENTRY(Caption); + STRUCTELEMENT_TYPE_ENTRY(NonStruct); + STRUCTELEMENT_TYPE_ENTRY(Index); + STRUCTELEMENT_TYPE_ENTRY(Private); + STRUCTELEMENT_TYPE_ENTRY(Span); + STRUCTELEMENT_TYPE_ENTRY(Quote); + STRUCTELEMENT_TYPE_ENTRY(Note); + STRUCTELEMENT_TYPE_ENTRY(Reference); + STRUCTELEMENT_TYPE_ENTRY(BibEntry); + STRUCTELEMENT_TYPE_ENTRY(Code); + STRUCTELEMENT_TYPE_ENTRY(Link); + STRUCTELEMENT_TYPE_ENTRY(Annot); + STRUCTELEMENT_TYPE_ENTRY(Ruby); + STRUCTELEMENT_TYPE_ENTRY(RB); + STRUCTELEMENT_TYPE_ENTRY(RT); + STRUCTELEMENT_TYPE_ENTRY(RP); + STRUCTELEMENT_TYPE_ENTRY(Warichu); + STRUCTELEMENT_TYPE_ENTRY(WT); + STRUCTELEMENT_TYPE_ENTRY(WP); + STRUCTELEMENT_TYPE_ENTRY(P); + STRUCTELEMENT_TYPE_ENTRY(H); + STRUCTELEMENT_TYPE_ENTRY(H1); + STRUCTELEMENT_TYPE_ENTRY(H2); + STRUCTELEMENT_TYPE_ENTRY(H3); + STRUCTELEMENT_TYPE_ENTRY(H4); + STRUCTELEMENT_TYPE_ENTRY(H5); + STRUCTELEMENT_TYPE_ENTRY(H6); + STRUCTELEMENT_TYPE_ENTRY(L); + STRUCTELEMENT_TYPE_ENTRY(LI); + STRUCTELEMENT_TYPE_ENTRY(Lbl); + STRUCTELEMENT_TYPE_ENTRY(LBody); + STRUCTELEMENT_TYPE_ENTRY(Table); + STRUCTELEMENT_TYPE_ENTRY(TR); + STRUCTELEMENT_TYPE_ENTRY(TH); + STRUCTELEMENT_TYPE_ENTRY(TD); + STRUCTELEMENT_TYPE_ENTRY(THead); + STRUCTELEMENT_TYPE_ENTRY(TFoot); + STRUCTELEMENT_TYPE_ENTRY(TBody); + STRUCTELEMENT_TYPE_ENTRY(Figure); + STRUCTELEMENT_TYPE_ENTRY(Formula); + STRUCTELEMENT_TYPE_ENTRY(Form); + STRUCTELEMENT_TYPE_ENTRY(TOC); + STRUCTELEMENT_TYPE_ENTRY(TOCI); + lua_pushstring(L, "Unknown"); + lua_pushinteger(L, 0); + lua_settable(L,-3); + return 1; +} + +static int l_AttributeOwner_Type(lua_State * L) { + lua_createtable (L, 0, 12); + lua_pushstring(L, "XML-1.00"); lua_pushinteger(L, Attribute::XML_1_00); lua_settable(L,-3); + lua_pushstring(L, "HTML-3.20"); lua_pushinteger(L, Attribute::HTML_3_20); lua_settable(L,-3); + lua_pushstring(L, "HTML-4.01"); lua_pushinteger(L, Attribute::HTML_4_01); lua_settable(L,-3); + lua_pushstring(L, "OEB-1.00"); lua_pushinteger(L, Attribute::OEB_1_00); lua_settable(L,-3); + lua_pushstring(L, "RTF-1.05"); lua_pushinteger(L, Attribute::RTF_1_05); lua_settable(L,-3); + lua_pushstring(L, "CSS-1.00"); lua_pushinteger(L, Attribute::CSS_1_00); lua_settable(L,-3); + lua_pushstring(L, "CSS-2.00"); lua_pushinteger(L, Attribute::CSS_2_00); lua_settable(L,-3); + lua_pushstring(L, "Layout"); lua_pushinteger(L, Attribute::Layout); lua_settable(L,-3); + lua_pushstring(L, "PrintField"); lua_pushinteger(L, Attribute::PrintField); lua_settable(L,-3); + lua_pushstring(L, "Table"); lua_pushinteger(L, Attribute::Table); lua_settable(L,-3); + lua_pushstring(L, "List"); lua_pushinteger(L, Attribute::List); lua_settable(L,-3); + lua_pushstring(L, "UserProperties"); lua_pushinteger(L, Attribute::UserProperties);lua_settable(L,-3); + return 1; +} + +static const struct luaL_Reg epdflib_f[] = { + {"open", l_open_PDFDoc}, + {"openMemStream", l_open_MemStreamPDFDoc}, + {"StructElement_Type", l_StructElement_Type}, + {"Attribute_Type", l_Attribute_Type}, + {"AttributeOwner_Type",l_AttributeOwner_Type}, + {"Object_Type", l_Object_Type}, + {NULL, NULL} +}; + +#define m_poppler_get_poppler(in, out, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + out *o; \ + udstruct *uin, *uout; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + o = ((in *) uin->d)->function(); \ + if (o != NULL) { \ + uout = new_##out##_userdata(L); \ + uout->d = o; \ + uout->pc = uin->pc; \ + uout->pd = uin->pd; \ + } else \ + lua_pushnil(L); \ + return 1; \ +} + +#define m_poppler_get_BOOL(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + if (((in *) uin->d)->function()) \ + lua_pushboolean(L, 1); \ + else \ + lua_pushboolean(L, 0); \ + return 1; \ +} + +#define m_poppler_get_INT(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + int i; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + i = (int) ((in *) uin->d)->function(); \ + lua_pushinteger(L, i); \ + return 1; \ +} + + +#define m_poppler_get_GUINT(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + unsigned int i; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + i = (unsigned int) ((in *) uin->d)->function(); \ + lua_pushinteger(L, i); \ + return 1; \ +} + +#define m_poppler_get_UINT(in, function) \ +m_poppler_get_GUINT(in, function) + + + +#define m_poppler_get_DOUBLE(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + double d; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + d = (double) ((in *) uin->d)->function(); \ + lua_pushnumber(L, d); /* float */ \ + return 1; \ +} + +#define m_poppler_get_GOOSTRING(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + GooString *gs; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + gs = ((in *) uin->d)->function(); \ + if (gs != NULL) \ + lua_pushlstring(L, gs->getCString(), gs->getLength()); \ + else \ + lua_pushnil(L); \ + return 1; \ +} + +#define m_poppler_get_OBJECT(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + udstruct *uin, *uout; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + uout = new_Object_userdata(L); \ + uout->d = new Object(); \ + *((Object *)uout->d) = ((in *) uin->d)->function(); \ + uout->atype = ALLOC_LEPDF; \ + uout->pc = uin->pc; \ + uout->pd = uin->pd; \ + return 1; \ +} + +#define m_poppler_do(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + ((in *) uin->d)->function(); \ + return 0; \ +} + +#define m_poppler__tostring(type) \ +static int m_##type##__tostring(lua_State * L) \ +{ \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##type); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + lua_pushfstring(L, "%s: %p", #type, (type *) uin->d); \ + return 1; \ +} + +#define m_poppler_check_string(in, function) \ +static int m_##in##_##function(lua_State * L) \ +{ \ + const char *s; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_##in); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + s = luaL_checkstring(L, 2); \ + if (((in *) uin->d)->function(s)) \ + lua_pushboolean(L, 1); \ + else \ + lua_pushboolean(L, 0); \ + return 1; \ +} + +/* Annot */ + +m_poppler_get_BOOL(Annot, isOk); + +static int m_Annot_match(lua_State * L) +{ + udstruct *uin, *uref; + uin = (udstruct *) luaL_checkudata(L, 1, M_Annot); + uref = (udstruct *) luaL_checkudata(L, 2, M_Ref); + if (uin->pd != NULL && uref->pd != NULL && uin->pd != uref->pd) + pdfdoc_differs_error(L); + if ((uin->pd != NULL && uin->pd->pc != uin->pc) + || (uref->pd != NULL && uref->pd->pc != uref->pc)) + pdfdoc_changed_error(L); + lua_pushboolean(L, ((Annot *) uin->d)->match((Ref *) uref->d)); + return 1; +} + +m_poppler__tostring(Annot); + +static int m_Annot__gc(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Annot); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); +#ifdef DEBUG + printf("\n===== Annot GC ===== uin=<%p>\n", uin); +#endif + if (uin->atype == ALLOC_LEPDF) +#if 1 /* def HAVE_ANNOTDECREFCNT */ + ((Annot *) uin->d)->decRefCnt(); +#else + delete(Annot *) uin->d; +#endif + return 0; +} + +static const struct luaL_Reg Annot_m[] = { + {"isOk", m_Annot_isOk}, + {"match", m_Annot_match}, + {"__tostring", m_Annot__tostring}, + {"__gc", m_Annot__gc}, + {NULL, NULL} +}; + +/* Annots */ + +m_poppler_get_INT(Annots, getNumAnnots); + +static int m_Annots_getAnnot(lua_State * L) +{ + int i, annots; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Annots); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + annots = ((Annots *) uin->d)->getNumAnnots(); + if (i > 0 && i <= annots) { + uout = new_Annot_userdata(L); + uout->d = ((Annots *) uin->d)->getAnnot(i); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +m_poppler__tostring(Annots); + +static const struct luaL_Reg Annots_m[] = { + {"getNumAnnots", m_Annots_getNumAnnots}, + {"getAnnot", m_Annots_getAnnot}, + {"__tostring", m_Annots__tostring}, + {NULL, NULL} +}; + +/* Array */ + +m_poppler_get_INT(Array, getLength); + +static int m_Array_get(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Array); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Array *) uin->d)->getLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Array *) uin->d)->get(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Array_getNF(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Array); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Array *) uin->d)->getLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Array *) uin->d)->getNF(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Array_getString(lua_State * L) +{ + GooString *gs; + int i, len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Array); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Array *) uin->d)->getLength(); + if (i > 0 && i <= len) { + gs = new GooString(); + if (((Array *) uin->d)->getString(i - 1, gs)) + lua_pushlstring(L, gs->getCString(), gs->getLength()); + else + lua_pushnil(L); + delete gs; + } else + lua_pushnil(L); + return 1; +} + +m_poppler__tostring(Array); + +static const struct luaL_Reg Array_m[] = { + {"getLength", m_Array_getLength}, + {"get", m_Array_get}, + {"getNF", m_Array_getNF}, + {"getString", m_Array_getString}, + {"__tostring", m_Array__tostring}, + {NULL, NULL} +}; + +/* Catalog */ + +m_poppler_get_BOOL(Catalog, isOk); +m_poppler_get_INT(Catalog, getNumPages); + +static int m_Catalog_getPage(lua_State * L) +{ + int i, pages; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Catalog); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + pages = ((Catalog *) uin->d)->getNumPages(); + if (i > 0 && i <= pages) { + uout = new_Page_userdata(L); + uout->d = ((Catalog *) uin->d)->getPage(i); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Catalog_getPageRef(lua_State * L) +{ + int i, pages; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Catalog); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + pages = ((Catalog *) uin->d)->getNumPages(); + if (i > 0 && i <= pages) { + uout = new_Ref_userdata(L); + uout->d = (Ref *) gmalloc(sizeof(Ref)); + ((Ref *) uout->d)->num = ((Catalog *) uin->d)->getPageRef(i)->num; + ((Ref *) uout->d)->gen = ((Catalog *) uin->d)->getPageRef(i)->gen; + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +m_poppler_get_GOOSTRING(Catalog, getBaseURI); +m_poppler_get_GOOSTRING(Catalog, readMetadata); +m_poppler_get_poppler(Catalog, StructTreeRoot, getStructTreeRoot); + +static int m_Catalog_findPage(lua_State * L) +{ + int num, gen, i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Catalog); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + num = luaL_checkint(L, 2); + gen = luaL_checkint(L, 3); + i = ((Catalog *) uin->d)->findPage(num, gen); + if (i > 0) + lua_pushinteger(L, i); + else + lua_pushnil(L); + return 1; +} + +static int m_Catalog_findDest(lua_State * L) +{ + GooString *name; + LinkDest *dest; + const char *s; + size_t len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Catalog); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checklstring(L, 2, &len); + name = new GooString(s, len); + dest = ((Catalog *) uin->d)->findDest(name); + if (dest != NULL) { + uout = new_LinkDest_userdata(L); + uout->d = dest; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + delete name; + return 1; +} + +m_poppler_get_poppler(Catalog, Object, getDests); +m_poppler_get_INT(Catalog, numEmbeddedFiles); + +static int m_Catalog_embeddedFile(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Catalog); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Catalog *) uin->d)->numEmbeddedFiles(); + if (i > 0 && i <= len) { + uout = new_FileSpec_userdata(L); + uout->d = ((Catalog *) uin->d)->embeddedFile(i - 1); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +m_poppler_get_INT(Catalog, numJS); + +static int m_Catalog_getJS(lua_State * L) +{ + GooString *gs; + int i, len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Catalog); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Catalog *) uin->d)->numJS(); + if (i > 0 && i <= len) { + gs = ((Catalog *) uin->d)->getJS(i - 1); + if (gs != NULL) + lua_pushlstring(L, gs->getCString(), gs->getLength()); + else + lua_pushnil(L); + delete gs; + } else + lua_pushnil(L); + return 1; +} + +m_poppler_get_poppler(Catalog, Object, getOutline); +m_poppler_get_poppler(Catalog, Object, getAcroForm); + +m_poppler__tostring(Catalog); + +static const struct luaL_Reg Catalog_m[] = { + {"isOk", m_Catalog_isOk}, + {"getNumPages", m_Catalog_getNumPages}, + {"getPage", m_Catalog_getPage}, + {"getPageRef", m_Catalog_getPageRef}, + {"getBaseURI", m_Catalog_getBaseURI}, + {"readMetadata", m_Catalog_readMetadata}, + {"getStructTreeRoot", m_Catalog_getStructTreeRoot}, + {"findPage", m_Catalog_findPage}, + {"findDest", m_Catalog_findDest}, + {"getDests", m_Catalog_getDests}, + {"numEmbeddedFiles", m_Catalog_numEmbeddedFiles}, + {"embeddedFile", m_Catalog_embeddedFile}, + {"numJS", m_Catalog_numJS}, + {"getJS", m_Catalog_getJS}, + {"getOutline", m_Catalog_getOutline}, + {"getAcroForm", m_Catalog_getAcroForm}, + {"__tostring", m_Catalog__tostring}, + {NULL, NULL} +}; + +/* Dict */ + +m_poppler_get_INT(Dict, getLength); + +m_poppler_check_string(Dict, is); + +static int m_Dict_lookup(lua_State * L) +{ + const char *s; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Dict); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Dict *) uin->d)->lookup(s); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +static int m_Dict_lookupNF(lua_State * L) +{ + const char *s; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Dict); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Dict *) uin->d)->lookupNF(s); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +static int m_Dict_lookupInt(lua_State * L) +{ + const char *s1, *s2; + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Dict); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s1 = luaL_checkstring(L, 2); + s2 = luaL_checkstring(L, 3); + if (((Dict *) uin->d)->lookupInt(s1, s2, &i)) + lua_pushinteger(L, i); + else + lua_pushnil(L); + return 1; +} + +static int m_Dict_getKey(lua_State * L) +{ + int i, len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Dict); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Dict *) uin->d)->getLength(); + if (i > 0 && i <= len) + lua_pushstring(L, ((Dict *) uin->d)->getKey(i - 1)); + else + lua_pushnil(L); + return 1; +} + +static int m_Dict_getVal(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Dict); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Dict *) uin->d)->getLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Dict *) uin->d)->getVal(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Dict_getValNF(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Dict); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + len = ((Dict *) uin->d)->getLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Dict *) uin->d)->getValNF(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +m_poppler_check_string(Dict, hasKey); + +m_poppler__tostring(Dict); + +static const struct luaL_Reg Dict_m[] = { + {"getLength", m_Dict_getLength}, + {"is", m_Dict_is}, + {"lookup", m_Dict_lookup}, + {"lookupNF", m_Dict_lookupNF}, + {"lookupInt", m_Dict_lookupInt}, + {"getKey", m_Dict_getKey}, + {"getVal", m_Dict_getVal}, + {"getValNF", m_Dict_getValNF}, + {"hasKey", m_Dict_hasKey}, + {"__tostring", m_Dict__tostring}, + {NULL, NULL} +}; + +/* EmbFile */ + +m_poppler_get_INT(EmbFile, size); +m_poppler_get_GOOSTRING(EmbFile, modDate); +m_poppler_get_GOOSTRING(EmbFile, createDate); +m_poppler_get_GOOSTRING(EmbFile, checksum); +m_poppler_get_GOOSTRING(EmbFile, mimeType); + +m_poppler_get_BOOL(EmbFile, isOk); + +static int m_EmbFile_save(lua_State * L) +{ + const char *s; + size_t len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_EmbFile); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checklstring(L, 2, &len); + if (((EmbFile *) uin->d)->save(s)) + lua_pushboolean(L, 1); + else + lua_pushboolean(L, 0); + return 1; +} + +m_poppler__tostring(EmbFile); + +static const struct luaL_Reg EmbFile_m[] = { + {"size", m_EmbFile_size}, + {"modDate", m_EmbFile_modDate}, + {"createDate", m_EmbFile_createDate}, + {"checksum", m_EmbFile_checksum}, + {"mimeType", m_EmbFile_mimeType}, + {"isOk", m_EmbFile_isOk}, + {"save", m_EmbFile_save}, + {"__tostring", m_EmbFile__tostring}, + {NULL, NULL} +}; + +/* FileSpec */ + +m_poppler_get_BOOL(FileSpec, isOk); +m_poppler_get_GOOSTRING(FileSpec, getFileName); +m_poppler_get_GOOSTRING(FileSpec, getFileNameForPlatform); +m_poppler_get_GOOSTRING(FileSpec, getDescription); + +static int m_FileSpec_getEmbeddedFile(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_FileSpec); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + uout = new_EmbFile_userdata(L); + uout->d = ((FileSpec *) uin->d)->getEmbeddedFile(); + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +m_poppler__tostring(FileSpec); + +static const struct luaL_Reg FileSpec_m[] = { + {"isOk", m_FileSpec_isOk}, + {"getFileName", m_FileSpec_getFileName}, + {"getFileNameForPlatform", m_FileSpec_getFileNameForPlatform}, + {"getDescription", m_FileSpec_getDescription}, + {"getEmbeddedFile", m_FileSpec_getEmbeddedFile}, + {"__tostring", m_FileSpec__tostring}, + {NULL, NULL} +}; + +/* GooString */ + +static int m_GooString__tostring(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_GooString); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + lua_pushlstring(L, ((GooString *) uin->d)->getCString(), + ((GooString *) uin->d)->getLength()); + return 1; +} + +static const struct luaL_Reg GooString_m[] = { + {"__tostring", m_GooString__tostring}, + {NULL, NULL} +}; + +/* LinkDest */ + +static const char *LinkDestKindNames[] = { + "XYZ", "Fit", "FitH", "FitV", "FitR", "FitB", "FitBH", "FitBV", + NULL +}; + +m_poppler_get_BOOL(LinkDest, isOk); + +static int m_LinkDest_getKind(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_LinkDest); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (int) ((LinkDest *) uin->d)->getKind(); + lua_pushinteger(L, i); + return 1; +} + +static int m_LinkDest_getKindName(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_LinkDest); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (int) ((LinkDest *) uin->d)->getKind(); + lua_pushstring(L, LinkDestKindNames[i]); + return 1; +} + +m_poppler_get_BOOL(LinkDest, isPageRef); +m_poppler_get_INT(LinkDest, getPageNum); + +static int m_LinkDest_getPageRef(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_LinkDest); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + uout = new_Ref_userdata(L); + uout->d = (Ref *) gmalloc(sizeof(Ref)); + ((Ref *) uout->d)->num = ((LinkDest *) uin->d)->getPageRef().num; + ((Ref *) uout->d)->gen = ((LinkDest *) uin->d)->getPageRef().gen; + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +m_poppler_get_DOUBLE(LinkDest, getLeft); +m_poppler_get_DOUBLE(LinkDest, getBottom); +m_poppler_get_DOUBLE(LinkDest, getRight); +m_poppler_get_DOUBLE(LinkDest, getTop); +m_poppler_get_DOUBLE(LinkDest, getZoom); +m_poppler_get_BOOL(LinkDest, getChangeLeft); +m_poppler_get_BOOL(LinkDest, getChangeTop); +m_poppler_get_BOOL(LinkDest, getChangeZoom); + +m_poppler__tostring(LinkDest); + +static const struct luaL_Reg LinkDest_m[] = { + {"isOk", m_LinkDest_isOk}, + {"getKind", m_LinkDest_getKind}, + {"getKindName", m_LinkDest_getKindName}, // not poppler + {"isPageRef", m_LinkDest_isPageRef}, + {"getPageNum", m_LinkDest_getPageNum}, + {"getPageRef", m_LinkDest_getPageRef}, + {"getLeft", m_LinkDest_getLeft}, + {"getBottom", m_LinkDest_getBottom}, + {"getRight", m_LinkDest_getRight}, + {"getTop", m_LinkDest_getTop}, + {"getZoom", m_LinkDest_getZoom}, + {"getChangeLeft", m_LinkDest_getChangeLeft}, + {"getChangeTop", m_LinkDest_getChangeTop}, + {"getChangeZoom", m_LinkDest_getChangeZoom}, + {"__tostring", m_LinkDest__tostring}, + {NULL, NULL} +}; + +/* Links */ + +m_poppler_get_INT(Links, getNumLinks); + +m_poppler__tostring(Links); + +static const struct luaL_Reg Links_m[] = { + {"getNumLinks", m_Links_getNumLinks}, + {"__tostring", m_Links__tostring}, + {NULL, NULL} +}; + +/* Object */ + +#ifdef HAVE_OBJECT_INITCMD_CONST_CHARP +#define CHARP_CAST +#else +/* + Must cast arg of Object::initCmd, Object::isStream, and Object::streamIs + from 'const char *' to 'char *', although they are not modified. +*/ +#define CHARP_CAST (char *) +#endif + +/* Special type checking. */ + +#define m_Object_isType_(function, cast) \ +static int m_Object_##function(lua_State * L) \ +{ \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + if (lua_gettop(L) >= 2) { \ + if (lua_isstring(L, 2) \ + && ((Object *) uin->d)->function(cast lua_tostring(L, 2))) \ + lua_pushboolean(L, 1); \ + else \ + lua_pushboolean(L, 0); \ + } else { \ + if (((Object *) uin->d)->function()) \ + lua_pushboolean(L, 1); \ + else \ + lua_pushboolean(L, 0); \ + } \ + return 1; \ +} + +#define m_Object_isType(function) m_Object_isType_(function, ) +#define m_Object_isType_nonconst(function) m_Object_isType_(function, CHARP_CAST) + +static int m_Object_fetch(lua_State * L) +{ + udstruct *uin, *uxref, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + uxref = (udstruct *) luaL_checkudata(L, 2, M_XRef); + if (uin->pd != NULL && uxref->pd != NULL && uin->pd != uxref->pd) + pdfdoc_differs_error(L); + if ((uin->pd != NULL && uin->pd->pc != uin->pc) + || (uxref->pd != NULL && uxref->pd->pc != uxref->pc)) + pdfdoc_changed_error(L); + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->fetch((XRef *) uxref->d); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +static int m_Object_getType(lua_State * L) +{ + ObjType t; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + t = ((Object *) uin->d)->getType(); + lua_pushinteger(L, (int) t); + return 1; +} + +static int m_Object_getTypeName(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + lua_pushstring(L, ((Object *) uin->d)->getTypeName()); + return 1; +} + +m_poppler_get_BOOL(Object, isBool); +m_poppler_get_BOOL(Object, isInt); +m_poppler_get_BOOL(Object, isReal); +m_poppler_get_BOOL(Object, isNum); +m_poppler_get_BOOL(Object, isString); +m_Object_isType(isName); +m_poppler_get_BOOL(Object, isNull); +m_poppler_get_BOOL(Object, isArray); +m_Object_isType(isDict); +m_Object_isType_nonconst(isStream); +m_poppler_get_BOOL(Object, isRef); +m_Object_isType(isCmd); +m_poppler_get_BOOL(Object, isError); +m_poppler_get_BOOL(Object, isEOF); +m_poppler_get_BOOL(Object, isNone); + +static int m_Object_getBool(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isBool()) { + if (((Object *) uin->d)->getBool()) + lua_pushboolean(L, 1); + else + lua_pushboolean(L, 0); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getInt(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isInt()) + lua_pushinteger(L, ((Object *) uin->d)->getInt()); + else + lua_pushnil(L); + return 1; +} + +static int m_Object_getReal(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isReal()) + lua_pushnumber(L, ((Object *) uin->d)->getReal()); /* float */ + else + lua_pushnil(L); + return 1; +} + +static int m_Object_getNum(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isInt()) + lua_pushinteger(L, ((Object *) uin->d)->getInt()); + else if (((Object *) uin->d)->isReal()) + lua_pushinteger(L, ((Object *) uin->d)->getReal()); + else if (((Object *) uin->d)->isNum()) /* redundant */ + lua_pushnumber(L, ((Object *) uin->d)->getNum()); /* integer or float */ + else + lua_pushnil(L); + return 1; +} + +static int m_Object_getString(lua_State * L) +{ + GooString *gs; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isString()) { + gs = ((Object *) uin->d)->getString(); + lua_pushlstring(L, gs->getCString(), gs->getLength()); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getName(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isName()) + lua_pushstring(L, ((Object *) uin->d)->getName()); + else + lua_pushnil(L); + return 1; +} + +static int m_Object_getArray(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isArray()) { + uout = new_Array_userdata(L); + uout->d = ((Object *) uin->d)->getArray(); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getDict(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isDict()) { + uout = new_Dict_userdata(L); + uout->d = ((Object *) uin->d)->getDict(); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getStream(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isStream()) { + uout = new_Stream_userdata(L); + uout->d = ((Object *) uin->d)->getStream(); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getRef(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isRef()) { + uout = new_Ref_userdata(L); + uout->d = (Ref *) gmalloc(sizeof(Ref)); + ((Ref *) uout->d)->num = ((Object *) uin->d)->getRef().num; + ((Ref *) uout->d)->gen = ((Object *) uin->d)->getRef().gen; + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getRefNum(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isRef()) { + i = ((Object *) uin->d)->getRef().num; + lua_pushinteger(L, i); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getRefGen(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isRef()) { + i = ((Object *) uin->d)->getRef().gen; + lua_pushinteger(L, i); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_getCmd(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isCmd()) + lua_pushstring(L, ((Object *) uin->d)->getCmd()); + else + lua_pushnil(L); + return 1; +} + +static int m_Object_arrayGetLength(lua_State * L) +{ + int len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isArray()) { + len = ((Object *) uin->d)->arrayGetLength(); + lua_pushinteger(L, len); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_arrayGet(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + if (((Object *) uin->d)->isArray()) { + len = ((Object *) uin->d)->arrayGetLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->arrayGet(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_arrayGetNF(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + if (((Object *) uin->d)->isArray()) { + len = ((Object *) uin->d)->arrayGetLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->arrayGetNF(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_dictGetLength(lua_State * L) +{ + int len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isDict()) { + len = ((Object *) uin->d)->dictGetLength(); + lua_pushinteger(L, len); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_dictLookup(lua_State * L) +{ + const char *s; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + if (((Object *) uin->d)->isDict()) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->dictLookup(s); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_dictLookupNF(lua_State * L) +{ + const char *s; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + if (((Object *) uin->d)->isDict()) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->dictLookupNF(s); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_dictGetKey(lua_State * L) +{ + int i, len; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + if (((Object *) uin->d)->isDict()) { + len = ((Object *) uin->d)->dictGetLength(); + if (i > 0 && i <= len) + lua_pushstring(L, ((Object *) uin->d)->dictGetKey(i - 1)); + else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_dictGetVal(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + if (((Object *) uin->d)->isDict()) { + len = ((Object *) uin->d)->dictGetLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->dictGetVal(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_dictGetValNF(lua_State * L) +{ + int i, len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + if (((Object *) uin->d)->isDict()) { + len = ((Object *) uin->d)->dictGetLength(); + if (i > 0 && i <= len) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((Object *) uin->d)->dictGetValNF(i - 1); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_streamIs(lua_State * L) +{ + const char *s; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + if (((Object *) uin->d)->isStream()) { + if (((Object *) uin->d)->streamIs(CHARP_CAST s)) + lua_pushboolean(L, 1); + else + lua_pushboolean(L, 0); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_streamReset(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isStream()) + ((Object *) uin->d)->streamReset(); + return 0; +} + +static int m_Object_streamGetChar(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isStream()) { + i = ((Object *) uin->d)->streamGetChar(); + lua_pushinteger(L, i); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_streamLookChar(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isStream()) { + i = ((Object *) uin->d)->streamLookChar(); + lua_pushinteger(L, i); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_streamGetPos(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isStream()) { + i = (int) ((Object *) uin->d)->streamGetPos(); + lua_pushinteger(L, i); + } else + lua_pushnil(L); + return 1; +} + +static int m_Object_streamSetPos(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + if (((Object *) uin->d)->isStream()) + ((Object *) uin->d)->streamSetPos(i); + return 0; +} + +static int m_Object_streamGetDict(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((Object *) uin->d)->isStream()) { + uout = new_Dict_userdata(L); + uout->d = ((Object *) uin->d)->streamGetDict(); + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_Object__gc(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Object); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); +#ifdef DEBUG + printf("\n===== Object GC ===== uin=<%p>\n", uin); +#endif + if (uin->atype == ALLOC_LEPDF) { + /* free() seems to collide with the lua gc */ + /* */ + /* ((Object *) uin->d)->free(); */ + /* */ + delete(Object *) uin->d; + } + return 0; +} + +m_poppler__tostring(Object); + +static const struct luaL_Reg Object_m[] = { + {"fetch", m_Object_fetch}, + {"getType", m_Object_getType}, + {"getTypeName", m_Object_getTypeName}, + {"isBool", m_Object_isBool}, + {"isInt", m_Object_isInt}, + {"isReal", m_Object_isReal}, + {"isNum", m_Object_isNum}, + {"isString", m_Object_isString}, + {"isName", m_Object_isName}, + {"isNull", m_Object_isNull}, + {"isArray", m_Object_isArray}, + {"isDict", m_Object_isDict}, + {"isStream", m_Object_isStream}, + {"isRef", m_Object_isRef}, + {"isCmd", m_Object_isCmd}, + {"isError", m_Object_isError}, + {"isEOF", m_Object_isEOF}, + {"isNone", m_Object_isNone}, + {"getBool", m_Object_getBool}, + {"getInt", m_Object_getInt}, + {"getReal", m_Object_getReal}, + {"getNum", m_Object_getNum}, + {"getString", m_Object_getString}, + {"getName", m_Object_getName}, + {"getArray", m_Object_getArray}, + {"getDict", m_Object_getDict}, + {"getStream", m_Object_getStream}, + {"getRef", m_Object_getRef}, + {"getRefNum", m_Object_getRefNum}, + {"getRefGen", m_Object_getRefGen}, + {"getCmd", m_Object_getCmd}, + {"arrayGetLength", m_Object_arrayGetLength}, + {"arrayGet", m_Object_arrayGet}, + {"arrayGetNF", m_Object_arrayGetNF}, + {"dictGetLength", m_Object_dictGetLength}, + {"dictLookup", m_Object_dictLookup}, + {"dictLookupNF", m_Object_dictLookupNF}, + {"dictGetKey", m_Object_dictGetKey}, + {"dictGetVal", m_Object_dictGetVal}, + {"dictGetValNF", m_Object_dictGetValNF}, + {"streamIs", m_Object_streamIs}, + {"streamReset", m_Object_streamReset}, + {"streamGetChar", m_Object_streamGetChar}, + {"streamLookChar", m_Object_streamLookChar}, + {"streamGetPos", m_Object_streamGetPos}, + {"streamSetPos", m_Object_streamSetPos}, + {"streamGetDict", m_Object_streamGetDict}, + {"__tostring", m_Object__tostring}, + {"__gc", m_Object__gc}, + {NULL, NULL} +}; + +/* Page */ + +m_poppler_get_BOOL(Page, isOk); +m_poppler_get_INT(Page, getNum); +m_poppler_get_poppler(Page, PDFRectangle, getMediaBox); +m_poppler_get_poppler(Page, PDFRectangle, getCropBox); +m_poppler_get_BOOL(Page, isCropped); +m_poppler_get_DOUBLE(Page, getMediaWidth); +m_poppler_get_DOUBLE(Page, getMediaHeight); +m_poppler_get_DOUBLE(Page, getCropWidth); +m_poppler_get_DOUBLE(Page, getCropHeight); +m_poppler_get_poppler(Page, PDFRectangle, getBleedBox); +m_poppler_get_poppler(Page, PDFRectangle, getTrimBox); +m_poppler_get_poppler(Page, PDFRectangle, getArtBox); +m_poppler_get_INT(Page, getRotate); +m_poppler_get_GOOSTRING(Page, getLastModified); +m_poppler_get_poppler(Page, Dict, getBoxColorInfo); +m_poppler_get_poppler(Page, Dict, getGroup); +m_poppler_get_poppler(Page, Stream, getMetadata); +m_poppler_get_poppler(Page, Dict, getPieceInfo); +m_poppler_get_poppler(Page, Dict, getSeparationInfo); +m_poppler_get_poppler(Page, Dict, getResourceDict); +m_poppler_get_OBJECT(Page, getAnnotsObject); + +m_poppler_get_OBJECT(Page, getContents); + +m_poppler__tostring(Page); + +static const struct luaL_Reg Page_m[] = { + {"isOk", m_Page_isOk}, + {"getNum", m_Page_getNum}, + {"getMediaBox", m_Page_getMediaBox}, + {"getCropBox", m_Page_getCropBox}, + {"isCropped", m_Page_isCropped}, + {"getMediaWidth", m_Page_getMediaWidth}, + {"getMediaHeight", m_Page_getMediaHeight}, + {"getCropWidth", m_Page_getCropWidth}, + {"getCropHeight", m_Page_getCropHeight}, + {"getBleedBox", m_Page_getBleedBox}, + {"getTrimBox", m_Page_getTrimBox}, + {"getArtBox", m_Page_getArtBox}, + {"getRotate", m_Page_getRotate}, + {"getLastModified", m_Page_getLastModified}, + {"getBoxColorInfo", m_Page_getBoxColorInfo}, + {"getGroup", m_Page_getGroup}, + {"getMetadata", m_Page_getMetadata}, + {"getPieceInfo", m_Page_getPieceInfo}, + {"getSeparationInfo", m_Page_getSeparationInfo}, + {"getResourceDict", m_Page_getResourceDict}, + {"getAnnotsObject", m_Page_getAnnotsObject}, + {"getContents", m_Page_getContents}, + {"__tostring", m_Page__tostring}, + {NULL, NULL} +}; + +/* PDFDoc */ + +#define m_PDFDoc_BOOL(function) \ +static int m_PDFDoc_##function(lua_State * L) \ +{ \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + if (((PdfDocument *) uin->d)->doc->function()) \ + lua_pushboolean(L, 1); \ + else \ + lua_pushboolean(L, 0); \ + return 1; \ +} + +#define m_PDFDoc_INT(function) \ +static int m_PDFDoc_##function(lua_State * L) \ +{ \ + int i; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + i = ((PdfDocument *) uin->d)->doc->function(); \ + lua_pushinteger(L, i); \ + return 1; \ +} + +m_PDFDoc_BOOL(isOk); +m_PDFDoc_INT(getErrorCode); + +static int m_PDFDoc_getFileName(lua_State * L) +{ + GooString *gs; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + gs = ((PdfDocument *) uin->d)->doc->getFileName(); + if (gs != NULL) + lua_pushlstring(L, gs->getCString(), gs->getLength()); + else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_getErrorCodeName(lua_State * L) +{ + int i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = ((PdfDocument *) uin->d)->doc->getErrorCode(); + lua_pushstring(L, ErrorCodeNames[i]); + return 1; +} + +static int m_PDFDoc_getXRef(lua_State * L) +{ + XRef *xref; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + xref = ((PdfDocument *) uin->d)->doc->getXRef(); + if (xref->isOk()) { + uout = new_XRef_userdata(L); + uout->d = xref; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_getCatalog(lua_State * L) +{ + Catalog *cat; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + cat = ((PdfDocument *) uin->d)->doc->getCatalog(); + if (cat->isOk()) { + uout = new_Catalog_userdata(L); + uout->d = cat; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +#define m_PDFDoc_PAGEDIMEN(function) \ +static int m_PDFDoc_##function(lua_State * L) \ +{ \ + int i, pages; \ + double d; \ + udstruct *uin; \ + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); \ + if (uin->pd != NULL && uin->pd->pc != uin->pc) \ + pdfdoc_changed_error(L); \ + i = luaL_checkint(L, 2); \ + pages = ((PdfDocument *) uin->d)->doc->getNumPages(); \ + if (i > 0 && i <= pages) { \ + d = (double) ((PdfDocument *) uin->d)->doc->function(i); \ + lua_pushnumber(L, d); /* float */ \ + } else \ + lua_pushnil(L); \ + return 1; \ +} + +m_PDFDoc_PAGEDIMEN(getPageMediaWidth); +m_PDFDoc_PAGEDIMEN(getPageMediaHeight); +m_PDFDoc_PAGEDIMEN(getPageCropWidth); +m_PDFDoc_PAGEDIMEN(getPageCropHeight); +m_PDFDoc_INT(getNumPages); + +static int m_PDFDoc_readMetadata(lua_State * L) +{ + GooString *gs; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((PdfDocument *) uin->d)->doc->getCatalog()->isOk()) { + gs = ((PdfDocument *) uin->d)->doc->readMetadata(); + if (gs != NULL) + lua_pushlstring(L, gs->getCString(), gs->getLength()); + else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_getStructTreeRoot(lua_State * L) +{ + StructTreeRoot *obj; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((PdfDocument *) uin->d)->doc->getCatalog()->isOk()) { + obj = ((PdfDocument *) uin->d)->doc->getStructTreeRoot(); + uout = new_StructTreeRoot_userdata(L); + uout->d = obj; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_findPage(lua_State * L) +{ + int num, gen, i; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + num = luaL_checkint(L, 2); + gen = luaL_checkint(L, 3); + if (((PdfDocument *) uin->d)->doc->getCatalog()->isOk()) { + i = ((PdfDocument *) uin->d)->doc->findPage(num, gen); + if (i > 0) + lua_pushinteger(L, i); + else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_getLinks(lua_State * L) +{ + int i, pages; + Links *links; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = luaL_checkint(L, 2); + pages = ((PdfDocument *) uin->d)->doc->getNumPages(); + if (i > 0 && i <= pages) { + links = ((PdfDocument *) uin->d)->doc->getLinks(i); + if (links != NULL) { + uout = new_Links_userdata(L); + uout->d = links; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_findDest(lua_State * L) +{ + GooString *name; + LinkDest *dest; + const char *s; + size_t len; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checklstring(L, 2, &len); + name = new GooString(s, len); + if (((PdfDocument *) uin->d)->doc->getCatalog()->isOk()) { + dest = ((PdfDocument *) uin->d)->doc->findDest(name); + if (dest != NULL) { + uout = new_LinkDest_userdata(L); + uout->d = dest; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + } else + lua_pushnil(L); + delete name; + return 1; +} + +m_PDFDoc_BOOL(isEncrypted); +m_PDFDoc_BOOL(okToPrint); +m_PDFDoc_BOOL(okToChange); +m_PDFDoc_BOOL(okToCopy); +m_PDFDoc_BOOL(okToAddNotes); +m_PDFDoc_BOOL(isLinearized); + +static int m_PDFDoc_getDocInfo(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((PdfDocument *) uin->d)->doc->getXRef()->isOk()) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((PdfDocument *) uin->d)->doc->getDocInfo(); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFDoc_getDocInfoNF(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + if (((PdfDocument *) uin->d)->doc->getXRef()->isOk()) { + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((PdfDocument *) uin->d)->doc->getDocInfoNF(); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +m_PDFDoc_INT(getPDFMajorVersion); +m_PDFDoc_INT(getPDFMinorVersion); + +m_poppler__tostring(PDFDoc); + +static int m_PDFDoc__gc(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFDoc); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); +#ifdef DEBUG + printf("\n===== PDFDoc GC ===== file_path=<%s>\n", + ((PdfDocument *) uin->d)->file_path); +#endif + assert(uin->atype == ALLOC_LEPDF); + unrefPdfDocument(((PdfDocument *) uin->d)->file_path); + return 0; +} + +static const struct luaL_Reg PDFDoc_m[] = { + {"isOk", m_PDFDoc_isOk}, + {"getErrorCode", m_PDFDoc_getErrorCode}, + {"getErrorCodeName", m_PDFDoc_getErrorCodeName}, // not poppler + {"getFileName", m_PDFDoc_getFileName}, + {"getXRef", m_PDFDoc_getXRef}, + {"getCatalog", m_PDFDoc_getCatalog}, + {"getPageMediaWidth", m_PDFDoc_getPageMediaWidth}, + {"getPageMediaHeight", m_PDFDoc_getPageMediaHeight}, + {"getPageCropWidth", m_PDFDoc_getPageCropWidth}, + {"getPageCropHeight", m_PDFDoc_getPageCropHeight}, + {"getNumPages", m_PDFDoc_getNumPages}, + {"readMetadata", m_PDFDoc_readMetadata}, + {"getStructTreeRoot", m_PDFDoc_getStructTreeRoot}, + {"findPage", m_PDFDoc_findPage}, + {"getLinks", m_PDFDoc_getLinks}, + {"findDest", m_PDFDoc_findDest}, + {"isEncrypted", m_PDFDoc_isEncrypted}, + {"okToPrint", m_PDFDoc_okToPrint}, + {"okToChange", m_PDFDoc_okToChange}, + {"okToCopy", m_PDFDoc_okToCopy}, + {"okToAddNotes", m_PDFDoc_okToAddNotes}, + {"isLinearized", m_PDFDoc_isLinearized}, + {"getDocInfo", m_PDFDoc_getDocInfo}, + {"getDocInfoNF", m_PDFDoc_getDocInfoNF}, + {"getPDFMajorVersion", m_PDFDoc_getPDFMajorVersion}, + {"getPDFMinorVersion", m_PDFDoc_getPDFMinorVersion}, + {"__tostring", m_PDFDoc__tostring}, + {"__gc", m_PDFDoc__gc}, + {NULL, NULL} +}; + +/* PDFRectangle */ + +m_poppler_get_BOOL(PDFRectangle, isValid); + +m_poppler__tostring(PDFRectangle); + +static int m_PDFRectangle__index(lua_State * L) +{ + const char *s; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFRectangle); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + if (strlen(s) == 2) { + if (s[0] == 'x') { + if (s[1] == '1') + lua_pushnumber(L, ((PDFRectangle *) uin->d)->x1); /* float */ + else if (s[1] == '2') + lua_pushnumber(L, ((PDFRectangle *) uin->d)->x2); /* float */ + else + lua_pushnil(L); + } else if (s[0] == 'y') { + if (s[1] == '1') + lua_pushnumber(L, ((PDFRectangle *) uin->d)->y1); /* float */ + else if (s[1] == '2') + lua_pushnumber(L, ((PDFRectangle *) uin->d)->y2); /* float */ + else + lua_pushnil(L); + } else + lua_pushnil(L); + } else + lua_pushnil(L); + return 1; +} + +static int m_PDFRectangle__newindex(lua_State * L) +{ + double d; + const char *s; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFRectangle); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + d = luaL_checknumber(L, 3); + if (strlen(s) == 2) { + if (s[0] == 'x') { + if (s[1] == '1') + ((PDFRectangle *) uin->d)->x1 = d; + else if (s[1] == '2') + ((PDFRectangle *) uin->d)->x2 = d; + else + luaL_error(L, "wrong PDFRectangle coordinate (%s)", s); + } else if (s[0] == 'y') { + if (s[1] == '1') + ((PDFRectangle *) uin->d)->y1 = d; + else if (s[1] == '2') + ((PDFRectangle *) uin->d)->y2 = d; + } else + luaL_error(L, "wrong PDFRectangle coordinate (%s)", s); + } else + luaL_error(L, "wrong PDFRectangle coordinate (%s)", s); + return 0; +} + +static int m_PDFRectangle__gc(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_PDFRectangle); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); +#ifdef DEBUG + printf("\n===== PDFRectangle GC ===== uin=<%p>\n", uin); +#endif + if (uin->atype == ALLOC_LEPDF) + delete(PDFRectangle *) uin->d; + return 0; +} + +static const struct luaL_Reg PDFRectangle_m[] = { + {"isValid", m_PDFRectangle_isValid}, + {"__index", m_PDFRectangle__index}, + {"__newindex", m_PDFRectangle__newindex}, + {"__tostring", m_PDFRectangle__tostring}, + {"__gc", m_PDFRectangle__gc}, + {NULL, NULL} +}; + +/* Ref */ + +static int m_Ref__index(lua_State * L) +{ + const char *s; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Ref); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + s = luaL_checkstring(L, 2); + if (strcmp(s, "num") == 0) + lua_pushinteger(L, ((Ref *) uin->d)->num); + else if (strcmp(s, "gen") == 0) + lua_pushinteger(L, ((Ref *) uin->d)->gen); + else + lua_pushnil(L); + return 1; +} + +m_poppler__tostring(Ref); + +static int m_Ref__gc(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Ref); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); +#ifdef DEBUG + printf("\n===== Ref GC ===== uin=<%p>\n", uin); +#endif + if (uin->atype == ALLOC_LEPDF && ((Ref *) uin->d) != NULL) + gfree(((Ref *) uin->d)); + return 0; +} + +static const struct luaL_Reg Ref_m[] = { + {"__index", m_Ref__index}, + {"__tostring", m_Ref__tostring}, + {"__gc", m_Ref__gc}, + {NULL, NULL} +}; + +/* Stream */ + +static const char *StreamKindNames[] = { + "File", "ASCIIHex", "ASCII85", "LZW", "RunLength", "CCITTFax", "DCT", + "Flate", "JBIG2", "JPX", "Weird", + NULL +}; + +m_poppler_get_INT(Stream, getKind); + +static int m_Stream_getKindName(lua_State * L) +{ + StreamKind t; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Stream); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + t = ((Stream *) uin->d)->getKind(); + lua_pushstring(L, StreamKindNames[t]); + return 1; +} + +m_poppler_do(Stream, reset); +m_poppler_do(Stream, close); +m_poppler_get_INT(Stream, getChar); +m_poppler_get_INT(Stream, lookChar); +m_poppler_get_INT(Stream, getRawChar); +m_poppler_get_INT(Stream, getUnfilteredChar); +m_poppler_do(Stream, unfilteredReset); +m_poppler_get_INT(Stream, getPos); +m_poppler_get_BOOL(Stream, isBinary); +m_poppler_get_poppler(Stream, Stream, getUndecodedStream); +m_poppler_get_poppler(Stream, Dict, getDict); + +m_poppler__tostring(Stream); + +static const struct luaL_Reg Stream_m[] = { + {"getKind", m_Stream_getKind}, + {"getKindName", m_Stream_getKindName}, // not poppler + {"reset", m_Stream_reset}, + {"close", m_Stream_close}, + {"getUndecodedStream", m_Stream_getUndecodedStream}, + {"getChar", m_Stream_getChar}, + {"lookChar", m_Stream_lookChar}, + {"getRawChar", m_Stream_getRawChar}, + {"getUnfilteredChar", m_Stream_getUnfilteredChar}, + {"unfilteredReset", m_Stream_unfilteredReset}, + {"getPos", m_Stream_getPos}, + {"isBinary", m_Stream_isBinary}, + {"getUndecodedStream", m_Stream_getUndecodedStream}, + {"getDict", m_Stream_getDict}, + {"__tostring", m_Stream__tostring}, + {NULL, NULL} +}; + +/* TextSpan */ + +m_poppler_get_GOOSTRING(TextSpan, getText); +m_poppler__tostring(TextSpan); + +static const struct luaL_Reg TextSpan_m[] = { + {"getText", m_TextSpan_getText}, + {"__tostring", m_TextSpan__tostring}, + {NULL, NULL} +}; + +/* Attribute */ + +m_poppler_get_BOOL(Attribute,isOk); +m_poppler_get_INT(Attribute,getType); +m_poppler_get_INT(Attribute,getOwner); +m_poppler_get_GOOSTRING(Attribute,getName); + +static int m_Attribute_getTypeName(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Attribute); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + lua_pushstring(L, ((Attribute *) uin->d)->getTypeName()); + return 1; +} + +static int m_Attribute_getOwnerName(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Attribute); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + lua_pushstring(L, ((Attribute *) uin->d)->getOwnerName()); + return 1; +} + +static int m_Attribute_getValue(lua_State * L) +{ + udstruct *uin, *uout; + Object *origin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Attribute); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + uout = new_Object_userdata(L); + uout->d = new Object(); + origin = (Object *) (((Attribute *) uin->d)->getValue()); + *((Object *) uout->d) = origin->copy(); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +static int m_Attribute_getDefaultValue(lua_State * L) +{ + Attribute::Type t; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_Attribute); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + t = (Attribute::Type) luaL_checkint(L, 2); + uout = new_Object_userdata(L); + uout->d = ((Attribute *)uin->d)->getDefaultValue(t) ; + //uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +m_poppler_get_GUINT(Attribute,getRevision); + +m_poppler_get_BOOL(Attribute, isHidden); + +static int m_Attribute_getFormattedValue(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Attribute); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + lua_pushstring(L, ((Attribute *) uin->d)->getFormattedValue()); + return 1; +} + +static int m_Attribute__gc(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_Attribute); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); +#ifdef DEBUG + printf("\n===== Attribute GC ===== uin=<%p>\n", uin); +#endif + if (uin->atype == ALLOC_LEPDF) { + delete(Attribute *) uin->d; + } + return 0; +} + +m_poppler__tostring(Attribute); + + +static const struct luaL_Reg Attribute_m[] = { + {"isOk",m_Attribute_isOk}, + {"getType",m_Attribute_getType}, + {"getOwner",m_Attribute_getOwner}, + {"getTypeName",m_Attribute_getTypeName}, + {"getOwnerName",m_Attribute_getOwnerName}, + {"getValue",m_Attribute_getValue}, + {"getDefaultValue",m_Attribute_getDefaultValue}, + {"getName",m_Attribute_getName}, + {"getRevision",m_Attribute_getRevision}, + {"isHidden",m_Attribute_isHidden}, + {"getFormattedValue",m_Attribute_getFormattedValue}, + {"__gc", m_Attribute__gc}, + {"__tostring", m_Attribute__tostring}, + {NULL, NULL} +}; + +/* StructElement */ + +m_poppler_get_INT(StructElement,getType); +m_poppler_get_BOOL(StructElement,isOk); +m_poppler_get_BOOL(StructElement,isBlock); +m_poppler_get_BOOL(StructElement,isInline); +m_poppler_get_BOOL(StructElement,isGrouping); +m_poppler_get_BOOL(StructElement,isContent); +m_poppler_get_BOOL(StructElement,isObjectRef); +m_poppler_get_BOOL(StructElement,hasPageRef); +m_poppler_get_INT(StructElement,getMCID); +m_poppler_get_INT(StructElement, getNumChildren); + +m_poppler_get_GUINT(StructElement,getRevision); +m_poppler_get_UINT(StructElement,getNumAttributes); + +m_poppler_get_GOOSTRING(StructElement, getID); +m_poppler_get_GOOSTRING(StructElement, getLanguage); +m_poppler_get_GOOSTRING(StructElement, getTitle); +m_poppler_get_GOOSTRING(StructElement, getExpandedAbbr); +m_poppler_get_GOOSTRING(StructElement, getAltText); +m_poppler_get_GOOSTRING(StructElement, getActualText); + +m_poppler_get_poppler(StructElement, StructTreeRoot, getStructTreeRoot); +m_poppler__tostring(StructElement); + +static int m_StructElement_getObjectRef(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + uout = new_Ref_userdata(L); + uout->d = (Ref *) gmalloc(sizeof(Ref)); + ((Ref *) uout->d)->num = ((StructElement *) uin->d)->getObjectRef().num; + ((Ref *) uout->d)->gen = ((StructElement *) uin->d)->getObjectRef().gen; + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +static int m_StructElement_getParentRef(lua_State * L) +{ + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + uout = new_Ref_userdata(L); + uout->d = (Ref *) gmalloc(sizeof(Ref)); + ((Ref *) uout->d)->num = ((StructElement *) uin->d)->getParentRef().num; + ((Ref *) uout->d)->gen = ((StructElement *) uin->d)->getParentRef().gen; + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +/* + Not exactly as the header: + + Ref = StructElement:getPageRef() + + Ref is false if the C++ function return false + +*/ + +static int m_StructElement_getPageRef(lua_State * L) +{ + GBool b; + Ref *r; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + r = (Ref *) gmalloc(sizeof(Ref)); + b = ((StructElement *) uin->d)->getPageRef( *r ); + if (b) { + uout = new_Ref_userdata(L); + uout->d = r ; + /* uout->atype = ALLOC_LEPDF; */ + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushboolean(L,0); + return 1; +} + +static int m_StructElement_getTypeName(lua_State * L) +{ + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + lua_pushstring(L, ((StructElement *) uin->d)->getTypeName()); + return 1; +} + +static int m_StructElement_getText(lua_State * L) +{ + GBool i; + GooString *gs; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (GBool) lua_toboolean(L, 2); + gs = ((StructElement *) uin->d)->getText(i); + if (gs != NULL) + lua_pushlstring(L, gs->getCString(), gs->getLength()); + else + lua_pushnil(L); + return 1; +} + +static int m_StructElement_getChild(lua_State * L) +{ + StructElement *c; + int i; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (int) luaL_checkint(L, 2); + c = ((StructElement *) uin->d)->getChild(i-1); + if (c != NULL) { + uout = new_StructElement_userdata(L); + uout->d = c ; + /* uout->atype = ALLOC_LEPDF; */ + uout->pc = uin->pc; + uout->pd = uin->pd; + } + else + lua_pushnil(L); + return 1; +} + +static int m_StructElement_getAttribute(lua_State * L) +{ + Attribute *a; + int i; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (int) luaL_checkint(L, 2); + a = ((StructElement *) uin->d)->getAttribute(i-1); + if (a != NULL) { + uout = new_Attribute_userdata(L); + uout->d = a ; + uout->pc = uin->pc; + uout->pd = uin->pd; + } + else + lua_pushnil(L); + return 1; +} + +static int m_StructElement_findAttribute(lua_State * L) +{ + Attribute::Type t; + Attribute::Owner o; + GBool g; + udstruct *uin, *uout; + const Attribute *a; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + t = (Attribute::Type) luaL_checkint(L,1); + o = (Attribute::Owner) luaL_checkint(L,2); + g = (GBool) lua_toboolean(L, 3); + a = ((StructElement *) uin->d)->findAttribute(t,g,o); + + if (a!=NULL){ + uout = new_Attribute_userdata(L); + uout->d = new Attribute(a->getType(),a->getValue()); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +/* This returns a lua table */ + +static int m_StructElement_getTextSpans(lua_State * L) +{ + int i ; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_StructElement); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + + if ((((StructElement *) uin->d)->getTextSpans()).size()>0) { + lua_createtable (L, + (int) (((StructElement *) uin->d)->getTextSpans()).size(), + 0); + for(i=0;i<(int) (((StructElement *) uin->d)->getTextSpans()).size(); i++){ + uout = new_TextSpan_userdata(L); + uout->d = new TextSpan( (((StructElement *) uin->d)->getTextSpans())[i] ); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + lua_rawseti(L,-2,i+1); + } + } else + lua_pushnil(L); + return 1; +} + +static const struct luaL_Reg StructElement_m[] = { + {"getTypeName", m_StructElement_getTypeName}, + {"getType",m_StructElement_getType}, + {"isOk",m_StructElement_isOk}, + {"isBlock",m_StructElement_isBlock}, + {"isInline",m_StructElement_isInline}, + {"isGrouping",m_StructElement_isGrouping}, + {"isContent",m_StructElement_isContent}, + {"isObjectRef",m_StructElement_isObjectRef}, + {"getMCID",m_StructElement_getMCID}, + {"getObjectRef",m_StructElement_getObjectRef}, + {"getParentRef",m_StructElement_getParentRef}, + {"hasPageRef",m_StructElement_hasPageRef}, + {"getPageRef",m_StructElement_getPageRef}, + {"getStructTreeRoot",m_StructElement_getStructTreeRoot}, + {"getID",m_StructElement_getID}, + {"getLanguage",m_StructElement_getLanguage}, + {"getRevision",m_StructElement_getRevision}, + {"getTitle",m_StructElement_getTitle}, + {"getExpandedAbbr",m_StructElement_getExpandedAbbr}, + {"getNumChildren",m_StructElement_getNumChildren}, + {"getChild",m_StructElement_getChild}, + {"getNumAttributes",m_StructElement_getNumAttributes}, + {"getAttribute",m_StructElement_getAttribute}, + {"findAttribute",m_StructElement_findAttribute}, + {"getAltText",m_StructElement_getAltText}, + {"getActualText",m_StructElement_getActualText}, + {"getText",m_StructElement_getText}, + {"getTextSpans",m_StructElement_getTextSpans}, + {"__tostring", m_StructElement__tostring}, + {NULL, NULL} +}; + +/* StructTreeRoot */ + +m_poppler_get_INT(StructTreeRoot, getNumChildren); +m_poppler_get_poppler(StructTreeRoot, PDFDoc, getDoc); +m_poppler_get_poppler(StructTreeRoot, Dict, getRoleMap); +m_poppler_get_poppler(StructTreeRoot, Dict, getClassMap); +m_poppler__tostring(StructTreeRoot); + +static int m_StructTreeRoot_getChild(lua_State * L) +{ + unsigned int i; + udstruct *uin, *uout; + StructElement *child ; + StructTreeRoot *root ; + + uin = (udstruct *) luaL_checkudata(L, 1, M_StructTreeRoot); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (unsigned) luaL_checkint(L, 2); + root = (StructTreeRoot *) uin->d; + if (i-1 < root->getNumChildren() ){ + child = root->getChild(i-1); + uout = new_StructElement_userdata(L); + uout->d = child; + /* uout->atype = ALLOC_LEPDF; */ + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static int m_StructTreeRoot_findParentElement(lua_State * L) +{ + unsigned int i; + udstruct *uin, *uout; + const StructElement *parent ; + StructTreeRoot *root ; + + uin = (udstruct *) luaL_checkudata(L, 1, M_StructTreeRoot); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + i = (unsigned) luaL_checkint(L, 2); + root = (StructTreeRoot *) uin->d; + parent = root->findParentElement(i-1); + if (parent != NULL) { + uout = new_StructElement_userdata(L); + /* see https://isocpp.org/wiki/faq/const-correctness#aliasing-and-const */ + uout->d = (StructElement *) parent; + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + } else + lua_pushnil(L); + return 1; +} + +static const struct luaL_Reg StructTreeRoot_m[] = { + {"getDoc",m_StructTreeRoot_getDoc}, + {"getRoleMap",m_StructTreeRoot_getRoleMap}, + {"getClassMap",m_StructTreeRoot_getClassMap}, + {"getNumChildren",m_StructTreeRoot_getNumChildren}, + {"getChild",m_StructTreeRoot_getChild}, + {"findParentElement",m_StructTreeRoot_findParentElement}, + {"__tostring", m_StructTreeRoot__tostring}, + {NULL, NULL} +}; + +/* XRef */ + +m_poppler_get_BOOL(XRef, isOk); +m_poppler_get_INT(XRef, getErrorCode); +m_poppler_get_BOOL(XRef, isEncrypted); +m_poppler_get_BOOL(XRef, okToPrint); +m_poppler_get_BOOL(XRef, okToPrintHighRes); +m_poppler_get_BOOL(XRef, okToChange); +m_poppler_get_BOOL(XRef, okToCopy); +m_poppler_get_BOOL(XRef, okToAddNotes); +m_poppler_get_BOOL(XRef, okToFillForm); +m_poppler_get_BOOL(XRef, okToAccessibility); +m_poppler_get_BOOL(XRef, okToAssemble); +m_poppler_get_OBJECT(XRef, getCatalog); + +static int m_XRef_fetch(lua_State * L) +{ + int num, gen; + udstruct *uin, *uout; + uin = (udstruct *) luaL_checkudata(L, 1, M_XRef); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + num = luaL_checkint(L, 2); + gen = luaL_checkint(L, 3); + uout = new_Object_userdata(L); + uout->d = new Object(); + *((Object *) uout->d) = ((XRef *) uin->d)->fetch(num, gen); + uout->atype = ALLOC_LEPDF; + uout->pc = uin->pc; + uout->pd = uin->pd; + return 1; +} + +m_poppler_get_OBJECT(XRef, getDocInfo); +m_poppler_get_OBJECT(XRef, getDocInfoNF); +m_poppler_get_INT(XRef, getNumObjects); +m_poppler_get_INT(XRef, getRootNum); +m_poppler_get_INT(XRef, getRootGen); + +static int m_XRef_getNumEntry(lua_State * L) +{ + int i, offset; + udstruct *uin; + uin = (udstruct *) luaL_checkudata(L, 1, M_XRef); + if (uin->pd != NULL && uin->pd->pc != uin->pc) + pdfdoc_changed_error(L); + offset = luaL_checkint(L, 2); + i = ((XRef *) uin->d)->getNumEntry(offset); + if (i >= 0) + lua_pushinteger(L, i); + else + lua_pushnil(L); + return 1; +} + +m_poppler_get_poppler(XRef, Object, getTrailerDict); + +m_poppler__tostring(XRef); + +static const struct luaL_Reg XRef_m[] = { + {"isOk", m_XRef_isOk}, + {"getErrorCode", m_XRef_getErrorCode}, + {"isEncrypted", m_XRef_isEncrypted}, + {"okToPrint", m_XRef_okToPrint}, + {"okToPrintHighRes", m_XRef_okToPrintHighRes}, + {"okToChange", m_XRef_okToChange}, + {"okToCopy", m_XRef_okToCopy}, + {"okToAddNotes", m_XRef_okToAddNotes}, + {"okToFillForm", m_XRef_okToFillForm}, + {"okToAccessibility", m_XRef_okToAccessibility}, + {"okToAssemble", m_XRef_okToAssemble}, + {"getCatalog", m_XRef_getCatalog}, + {"fetch", m_XRef_fetch}, + {"getDocInfo", m_XRef_getDocInfo}, + {"getDocInfoNF", m_XRef_getDocInfoNF}, + {"getNumObjects", m_XRef_getNumObjects}, + {"getRootNum", m_XRef_getRootNum}, + {"getRootGen", m_XRef_getRootGen}, + {"getNumEntry", m_XRef_getNumEntry}, + {"getTrailerDict", m_XRef_getTrailerDict}, + {"__tostring", m_XRef__tostring}, + {NULL, NULL} +}; + +/* XRefEntry */ + +m_poppler__tostring(XRefEntry); + +static const struct luaL_Reg XRefEntry_m[] = { + {"__tostring", m_XRefEntry__tostring}, + {NULL, NULL} +}; + +/* Done */ + +#ifdef LuajitTeX +#define setfuncs_meta(type) \ + luaL_newmetatable(L, M_##type); \ + lua_pushvalue(L, -1); \ + lua_setfield(L, -2, "__index"); \ + lua_pushstring(L, "no user access"); \ + lua_setfield(L, -2, "__metatable"); \ + luaL_openlib(L, NULL, type##_m, 0) +#else +#define setfuncs_meta(type) \ + luaL_newmetatable(L, M_##type); \ + lua_pushvalue(L, -1); \ + lua_setfield(L, -2, "__index"); \ + lua_pushstring(L, "no user access"); \ + lua_setfield(L, -2, "__metatable"); \ + luaL_setfuncs(L, type##_m, 0) +#endif + +int luaopen_epdf(lua_State * L) +{ + setfuncs_meta(Annot); + setfuncs_meta(Annots); + setfuncs_meta(Array); + setfuncs_meta(Catalog); + setfuncs_meta(Dict); + setfuncs_meta(EmbFile); + setfuncs_meta(FileSpec); + setfuncs_meta(GooString); + setfuncs_meta(LinkDest); + setfuncs_meta(Links); + setfuncs_meta(Object); + setfuncs_meta(Page); + setfuncs_meta(PDFDoc); + setfuncs_meta(PDFRectangle); + setfuncs_meta(Ref); + setfuncs_meta(Stream); + setfuncs_meta(Attribute); + setfuncs_meta(StructElement); + setfuncs_meta(StructTreeRoot); + setfuncs_meta(TextSpan); + setfuncs_meta(XRef); + setfuncs_meta(XRefEntry); + luaL_openlib(L, "epdf", epdflib_f, 0); + return 1; +} diff --git a/Build/source/texk/web2c/luatexdir/lua/lfontlib.c b/Build/source/texk/web2c/luatexdir/lua/lfontlib.c index b3ac2aa536e..92d60a80c7d 100644 --- a/Build/source/texk/web2c/luatexdir/lua/lfontlib.c +++ b/Build/source/texk/web2c/luatexdir/lua/lfontlib.c @@ -44,7 +44,7 @@ static int font_read_tfm(lua_State * L) if (strlen(cnom)) { internal_font_number f = get_fontid(); if (read_tfm_info(f, cnom, s)) { - int k = font_to_lua(L, f); + int k = font_to_lua(L, f, 0); delete_font(f); return k; } else { @@ -118,7 +118,7 @@ static int tex_each_font_next(lua_State * L) return 1; } else { lua_pushinteger(L, i); - if (!font_to_lua(L, i)) + if (!font_to_lua(L, i, 1)) lua_pushnil(L); return 2; } @@ -251,7 +251,16 @@ static int nextfontid(lua_State * L) static int getfont(lua_State * L) { int i = luaL_checkinteger(L, -1); - if (i && is_valid_font(i) && font_to_lua(L, i)) + if (i && is_valid_font(i) && font_to_lua(L, i, 1)) + return 1; + lua_pushnil(L); + return 1; +} + +static int getcopy(lua_State * L) +{ + int i = luaL_checkinteger(L, -1); + if (i && is_valid_font(i) && font_to_lua(L, i, 0)) return 1; lua_pushnil(L); return 1; @@ -293,6 +302,7 @@ static const struct luaL_Reg fontlib[] = { {"max", tex_max_font}, {"each", tex_each_font}, {"getfont", getfont}, + {"getcopy", getcopy}, {"getparameters", getparameters}, {"setfont", setfont}, {"addcharacters", addcharacters}, diff --git a/Build/source/texk/web2c/luatexdir/lua/lnewtokenlib.c b/Build/source/texk/web2c/luatexdir/lua/lnewtokenlib.c index a50ea2f20d9..d1ef55ad188 100644 --- a/Build/source/texk/web2c/luatexdir/lua/lnewtokenlib.c +++ b/Build/source/texk/web2c/luatexdir/lua/lnewtokenlib.c @@ -1164,6 +1164,9 @@ static int set_macro(lua_State * L) if (n == 1) return 0; ct = (int) lua_tointeger(L, 1); + if (!valid_catcode_table(ct)) { + ct = cat_code_table_par; + } name = lua_tolstring(L, 2, &lname); if (n > 2) str = lua_tolstring(L, 3, &lstr); @@ -1224,10 +1227,14 @@ static int set_macro(lua_State * L) str += _s ; break ; } else { + if (_lname == 0) { + _lname = _lname + _s ; + str += _s ; + } break ; } } - if (_s > 0) { + if (_lname > 0) { /* we have a potential \cs */ _cs = string_lookup(_name, _lname); if (_cs == undefined_control_sequence) { diff --git a/Build/source/texk/web2c/luatexdir/lua/lpdfelib.c b/Build/source/texk/web2c/luatexdir/lua/lpdfelib.c index 455ed9b0479..5b1093a28a5 100644 --- a/Build/source/texk/web2c/luatexdir/lua/lpdfelib.c +++ b/Build/source/texk/web2c/luatexdir/lua/lpdfelib.c @@ -45,7 +45,7 @@ # undef output # endif -# include "luapplib/pplib.h" +# include "luapplib/src/pplib.h" # include "image/epdf.h" @@ -422,12 +422,15 @@ static int pushvalue(lua_State * L, ppobj *object) return 1; break; case PPNAME: - lua_pushstring(L, (const char *) ppname_decoded(object->name)); - return 1; + { + ppname * n = ppname_decoded(object->name) ; + lua_pushlstring(L, ppname_data(n), ppname_size(n)); + return 1; + } break; case PPSTRING: - lua_pushlstring(L,(const char *) object->string, ppstring_size((void *)object->string)); - lua_pushboolean(L, ppstring_hex((void *)object->string)); + lua_pushlstring(L, ppstring_data(object->string), ppstring_size(object->string)); + lua_pushboolean(L, ppstring_hex(object->string)); return 2; break; case PPARRAY: @@ -527,8 +530,8 @@ static int pdfelib_getfromdictionary(lua_State * L) if (index < d->dictionary->size) { ppobj *object = ppdict_at(d->dictionary,index); if (object != NULL) { - ppname key = ppdict_key(d->dictionary,index); - lua_pushstring(L,(const char *) key); + ppname * key = ppname_decoded(ppdict_key(d->dictionary,index)); + lua_pushlstring(L, ppname_data(key), ppname_size(key)); lua_pushinteger(L,(int) object->type); return 2 + pushvalue(L,object); } @@ -555,8 +558,8 @@ static int pdfelib_getfromstream(lua_State * L) if (index < d->size) { ppobj *object = ppdict_at(d,index); if (object != NULL) { - ppname key = ppdict_key(d,index); - lua_pushstring(L,(const char *) key); + ppname * key = ppname_decoded(ppdict_key(d,index)); + lua_pushlstring(L, ppname_data(key), ppname_size(key)); lua_pushinteger(L,(int) object->type); return 2 + pushvalue(L,object); } @@ -656,8 +659,8 @@ static int pdfelib_dictionarytotable(lua_State * L) for (i=0;idictionary->size;i++) { ppobj *object = ppdict_at(d->dictionary,i); if (object != NULL) { - ppname key = ppdict_key(d->dictionary,i); - lua_pushstring(L,(const char *) key); + ppname * key = ppname_decoded(ppdict_key(d->dictionary,i)); + lua_pushlstring(L, ppname_data(key), ppname_size(key)); /* table key */ pdfelib_totable(L,object,flat); /* table key { type, [value], [extra], [more] } */ @@ -874,7 +877,7 @@ static int pdfelib_new(lua_State * L) if (! memstream) { luaL_error(L, "no room for stream"); } - memcpy(memstream, docstream, (streamsize + 1)); + memcpy(memstream, docstream, streamsize); memstream[streamsize]='\0'; if (lua_gettop(L) == 2) { /* we stay at the lua end */ @@ -1011,7 +1014,6 @@ static int pdfelib_getsize(lua_State * L) return 1; } - static int pdfelib_getversion(lua_State * L) { pdfe_document *p = check_isdocument(L, 1); @@ -1321,10 +1323,10 @@ static int pdfelib_getfromreference(lua_State * L) static int pdfelib_getstring(lua_State * L) { if (lua_gettop(L) > 1) { - ppstring value = NULL; + ppstring * value = NULL; pdfelib_get_value_direct(ppdict_rget_string,pparray_rget_string); if (value != NULL) { - lua_pushstring(L,(const char *) value); + lua_pushlstring(L, ppstring_data(value), ppstring_size(value)); return 1; } } @@ -1376,10 +1378,11 @@ static int pdfelib_getboolean(lua_State * L) static int pdfelib_getname(lua_State * L) { if (lua_gettop(L) > 1) { - ppname value = NULL; + ppname * value = NULL; pdfelib_get_value_direct(ppdict_rget_name,pparray_rget_name); if (value != NULL) { - lua_pushstring(L,(const char *) ppname_decoded(value)); + value = ppname_decoded(value) ; + lua_pushlstring(L, ppname_data(value), ppname_size(value)); return 1; } } @@ -1446,10 +1449,13 @@ static int pdfelib_pushvalue(lua_State * L, ppobj *object) lua_pushnumber(L, object->number); break; case PPNAME: - lua_pushstring(L, (const char *) ppname_decoded(object->name)); + { + ppname * n = ppname_decoded(object->name) ; + lua_pushlstring(L, ppname_data(n), ppname_size(n)); + } break; case PPSTRING: - lua_pushlstring(L,(const char *) object->string, ppstring_size((void *)object->string)); + lua_pushlstring(L, ppstring_data(object->string), ppstring_size(object->string)); break; case PPARRAY: return pusharrayonly(L, object->array); diff --git a/Build/source/texk/web2c/luatexdir/lua/lpdfscannerlib.c b/Build/source/texk/web2c/luatexdir/lua/lpdfscannerlib.c index 6c3bc8876ee..4fc62a2ccf9 100644 --- a/Build/source/texk/web2c/luatexdir/lua/lpdfscannerlib.c +++ b/Build/source/texk/web2c/luatexdir/lua/lpdfscannerlib.c @@ -78,7 +78,7 @@ #include #include -#include "luapplib/pplib.h" +#include "luapplib/src/pplib.h" #include diff --git a/Build/source/texk/web2c/luatexdir/lua/luainit.c b/Build/source/texk/web2c/luatexdir/lua/luainit.c index 7570910b0ef..4926d8bd382 100644 --- a/Build/source/texk/web2c/luatexdir/lua/luainit.c +++ b/Build/source/texk/web2c/luatexdir/lua/luainit.c @@ -677,6 +677,7 @@ static int luatex_kpse_lua_find(lua_State * L) /*tex library not found in this path */ return 1; } + recorder_record_input(filename); if (luaL_loadfile(L, filename) != 0) { luaL_error(L, "error loading module %s from file %s:\n\t%s", lua_tostring(L, 1), filename, lua_tostring(L, -1)); @@ -714,6 +715,7 @@ static int luatex_kpse_clua_find(lua_State * L) /*tex library not found in this path */ return 1; } + recorder_record_input(filename); extensionless = strdup(filename); if (!extensionless) { /*tex allocation failure */ diff --git a/Build/source/texk/web2c/luatexdir/lua/luatex-api.h b/Build/source/texk/web2c/luatexdir/lua/luatex-api.h index bebf088af99..14650ffdcee 100644 --- a/Build/source/texk/web2c/luatexdir/lua/luatex-api.h +++ b/Build/source/texk/web2c/luatexdir/lua/luatex-api.h @@ -155,7 +155,7 @@ extern int luaopen_stats(lua_State * L); extern int luaopen_font(lua_State * L); extern int luaopen_vf(lua_State * L); extern int font_parameters_to_lua(lua_State * L, int f); -extern int font_to_lua(lua_State * L, int f); +extern int font_to_lua(lua_State * L, int f, int usecache); extern int font_from_lua(lua_State * L, int f); /* return is boolean */ extern int characters_from_lua(lua_State * L, int f); /* return is boolean */ diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/README-win.md b/Build/source/texk/web2c/luatexdir/luaharfbuzz/README-win.md deleted file mode 100644 index d7a769ffa4b..00000000000 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/README-win.md +++ /dev/null @@ -1,53 +0,0 @@ -# Building Harfbuzz and _luaharfbuzz_ on Windows - -## Building Harfbuzz - -### Prerequisites -* [Visual Studio Community Edition](https://www.visualstudio.com/vs/community/) -* C++ Support for Visual Studio (See [here](http://stackoverflow.com/questions/31953769/visual-studio-doesnt-have-cl-exe)) - -### Building -* Download the Harfbuzz source for win32 from the [releases pages](https://github.com/behdad/harfbuzz/releases) (look for a zip file that ends with _-win32_, for e.g. _harfbuzz-1.4.2-win32.zip_), and unzip it. -* Launch the Visual Studio developer prompt for the platform you want to target. This is very important. For e.g, on my 64-bit system, I am using _VS2015 x64 Native Tools Command Prompt_ -* Navigate to the _win32_ folder in the Harfbuzz source tree and do `nmake /f Makefile.vc CFG=release` -* This should generate _harfbuzz.lib_ and _harfbuzz-vs14.dll_. - -## Copying Harfbuzz headers and DLL to the right locations -The Harfbuzz headers and DLLs must be copied to the right locations, for Lua and LuaRocks to be able to find them during installation and running: - -* Copy all the Harfbuzz header (_src/*.h_) files to _C:\external\include\harfbuzz_. This is where LuaRocks will look for them by default. Make sure the header files are in the _harfbuzz_ sub-directory under _C:\external\include_, otherwise it will not work. -* Copy _harfbuzz.lib_ and _harfbuzz-vs14.dll_ to the folder _C:\external\lib_. This is where LuaRocks will look for them by default. -* Copy _harfbuzz-vs14.dll_ to _C:\Windows\System32_. This is where running programs can locate the Harfbuzz DLL. - -## Installing Lua and LuaRocks -It is highly recommended that you install Lua 5.2 and LuaRocks in a sandboxed environment on your machine. [Hererocks] makes it dead simple to do on Windows. Make sure you have installed Python first. On my system, I just did `chocolatey install python`, but you can use an alternate method and skip running that command below. - -[Hererocks]:https://github.com/mpeterv/hererocks - -``` -chocolatey install python -wget https://raw.githubusercontent.com/mpeterv/hererocks/latest/hererocks.py -python hererocks.py lua52 -l5.2 -rlatest -source lua52/bin/activate -``` -## Install _luaharfbuzz_ -If you followed the steps in the previous sections, and have a sandboxed Lua installation, which the Lua program on %PATH%, then doing the following should just work: - -``` -C:\> luarocks install luaharfbuzz -``` - -This will download the _luaharfbuzz_ source, compile the C modules, link them against Lua and Harfbuzz, and install it in the right location. - -## Test -Test whether the installation was successful by loading _luaharfbuzz_ in the Lua REPL - -``` -C:\> lua -Lua 5.2.4 Copyright (C) 1994-2015 Lua.org, PUC-Rio -> hb = require("harfbuzz") -> print(hb.version()) -1.4.1 -> -``` - diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/README.md b/Build/source/texk/web2c/luatexdir/luaharfbuzz/README.md index f5a900c65b1..c5cee58f869 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/README.md +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/README.md @@ -19,10 +19,17 @@ HarfBuzz is an OpenType text shaping engine. It is used in software like Qt, Pango, Firefox, Chromium, XeTeX and LibreOffice. _luaharfbuzz_ provides bindings for the most common types in Harfbuzz. The -initial motivation for building it is to use Harfbuzz with the [LuaTeX] +initial motivation for building it was to use Harfbuzz with the [LuaTeX] typesetting system. However, the module isn’t tied to LuaTeX in any way. It can be used with any Lua codebase. +luaharfbuzz is currently being used inside [HarfTeX], a TeX engine built +on top of LuaTeX and designed to use Harfbuzz for shaping text. For more +details read this TUGboat journal article titled [Bringing world scripts to LuaTeX: The +HarfBuzz experiment][tugboat-article] + +[HarfTeX]: https://github.com/khaledhosny/harftex +[tugboat-article]: https://tug.org/TUGboat/tb40-1/tb124hosny-harfbuzz.pdf [LuaTeX]:luatex.org ## Installing Harfbuzz @@ -43,9 +50,6 @@ brew install harfbuzz apt-get install libharfbuzz0b libharfbuzz-dev ``` -#### Windows -Getting the whole setup running on Windows is very tedious, so all instructions are in their own file [README-win.md](https://github.com/deepakjois/luaharfbuzz/blob/master/README-win.md). - #### Other Platforms _Send a pull request if you want to include specific instructions to install Harfbuzz on your preferred platform._ @@ -139,6 +143,8 @@ In order to make changes to the code and run the tests, the following dependenci * [Busted](http://olivinelabs.com/busted/) – `luarocks install busted` * [luacheck](luacheck.readthedocs.org) – `luarocks install luacheck` +* [luacov](https://keplerproject.github.io/luacov/) – `luarocks install luacov` +* [ldoc](https://stevedonovan.github.io/ldoc/) – `luarocks install ldoc` Run the test suite: ``` @@ -150,5 +156,10 @@ Lint the codebase: make lint ``` +Generate documentation from sources: +``` +make doc +``` + ## Contact Open a Github issue, or email me at . diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/config.ld b/Build/source/texk/web2c/luatexdir/luaharfbuzz/config.ld index 95d27f9a39f..d37be652ca9 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/config.ld +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/config.ld @@ -1,6 +1,6 @@ project = 'luaharfbuzz' description = 'Lua bindings to Harfbuzz' -full_description = 'The documentation is available on the @{https://github.com/deepakjois/luaharfbuzz/wiki|wiki}' +full_description = 'The documentation is available on the @{https://github.com/ufytex/luaharfbuzz/wiki|wiki}' use_markdown_titles = true backtick_references = false title = 'luaharfbuzz Documentation' diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/core_types.lua.html b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/core_types.lua.html index fe9e5c39c9b..6345ea3c6fa 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/core_types.lua.html +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/core_types.lua.html @@ -101,7 +101,7 @@ glyphs = buf:get_glyphs()
generated by LDoc 1.4.6 -Last updated 2019-04-13 17:03:03 +Last updated 2019-07-31 18:39:39
diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/custom_callbacks.lua.html b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/custom_callbacks.lua.html deleted file mode 100644 index eff09e27b8d..00000000000 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/custom_callbacks.lua.html +++ /dev/null @@ -1,85 +0,0 @@ - - - - - luaharfbuzz Documentation - - - - -
- -
- -
-
-
- - -
- - - - - - -
- -

custom_callbacks.lua

-
--- Switch off some callbacks
-callback.register("hyphenate", false)
-callback.register("ligaturing", false)
-callback.register("kerning", false)
-
--- Add debug statements to some callbacks
-callback.register("post_linebreak_filter", function()
-  texio.write_nl("POST_LINEBREAK")
-  return true
-end)
-
-callback.register("hpack_filter", function()
-  texio.write_nl("HPACK")
-  return true
-end)
-
-callback.register("vpack_filter", function()
-  texio.write_nl("VPACK")
-  return true
-end)
-
-callback.register("buildpage_filter", function(extrainfo)
-  texio.write_nl("BUILDPAGE_FILTER "..extrainfo)
-end)
- - -
-
-
-generated by LDoc 1.4.5 -Last updated 2016-08-31 21:59:58 -
-
- - diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/harfbuzz_setup.lua.html b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/harfbuzz_setup.lua.html deleted file mode 100644 index dba607a9f6c..00000000000 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/harfbuzz_setup.lua.html +++ /dev/null @@ -1,231 +0,0 @@ - - - - - luaharfbuzz Documentation - - - - -
- -
- -
-
-
- - -
- - - - - - -
- -

harfbuzz_setup.lua

-
--- Allow external Lua modules to be loaded.
-dofile 'package_path_searcher.lua'
-
--- Attach a OpenType font loader to define_font callback.
-require 'ot_font_loader'
-
--- Disable some callbacks, and attach debug logging to others.
-require 'custom_callbacks'
-
--- List all callbacks
-local serpent = require 'serpent'
-texio.write_nl(serpent.block(callback.list()))
-
--- Load luaharfbuzz
-local harfbuzz = require 'harfbuzz'
-
-local lt_to_hb_dir = { TLT = "ltr", TRT = "rtl" }
--- local hb_to_lt_dir = { ltr = "TLT", rtl = "TRT" }
-
-local function upem_to_sp(v,font)
-  return math.floor(v / font.units_per_em * font.size)
-end
-
--- Print the contents of a nodelist.
--- Glyph nodes are printed as UTF-8 characters, while other nodes are printed
--- by calling node.type on it, along with the subtype of the node.
-local function show_nodes (head, raw)
-  local nodes = ''
-  for item in node.traverse(head) do
-    local i = item.id
-    if i == node.id("glyph") then
-      if raw then i = string.format('<glyph %d>', item.char) else i = unicode.utf8.char(item.char) end
-    else
-      i = string.format('<%s%s>', node.type(i), ( item.subtype and ("(".. item.subtype .. ")") or ''))
-    end
-    nodes = nodes .. i .. ' '
-  end
-  texio.write_nl(nodes)
-  return true
-end
-
--- Process a paragraph nodelist and shape it with Harfbuzz.
--- Only works for the most simple paragraphs. Check the assertions in the code
--- to understand what kind of nodes the shaping routine is expecting at
--- any point.
-local function process_nodes(head)
-  -- Pointer to traverse head nodelist
-  local head_slider = head
-
-  -- First node is a local_par
-  assert(head_slider.id == node.id("local_par"), "local_par expected")
-
-  -- Get direction
-  local dir = head_slider.dir
-  texio.write_nl("direction is: "..dir)
-
-
-  -- Second node is indentation
-  head_slider = head_slider.next
-  assert(head_slider.id == node.id("hlist") and head_slider.subtype == 3, "parindent hlist expected")
-
-  -- Check if font can be shaped by Harfbuzz
-  local fontid = head_slider.next.font
-  texio.write_nl("fontid is "..fontid)
-  local font = font.getfont(fontid)
-  if not font.harfbuzz then return head end
-  texio.write_nl("paragraph can be shaped by Harfbuzz")
-
-  -- Initialise new head
-  local new_head = node.copy_list(head, head_slider.next)
-  assert(node.length(new_head) == 2, "expected two nodes in new_head")
-
-  -- Pointer to traverse new heade nodelist
-  local new_head_slider = node.slide(new_head)
-
-  -- Build text
-  local codepoints = { }
-  while head_slider.next.id ~= node.id("penalty") do
-    head_slider = head_slider.next
-    if head_slider.id == node.id("glyph") then
-      table.insert(codepoints, head_slider.char)
-    elseif head_slider.id == node.id("glue") and head_slider.subtype == 13 then
-      table.insert(codepoints, 0x20)
-    else
-      error(string.format("Cant handle node of type %s, subtype %s", node.type(head_slider.id), tostring(head_slider.subtype)))
-    end
-  end
-
-  -- Initialise new tail at the last penalty node.
-  local new_tail = head_slider.next
-
-  -- Skip over penalty node
-  head_slider = head_slider.next.next
-
-  -- Last node is a \parfillskip
-  assert(head_slider.id == node.id("glue") and head_slider.subtype == 15, "\\parfillskip expected")
-  assert(not head_slider.next, "Expected this to be the last node.")
-
-  -- Shape text
-  local buf = harfbuzz.Buffer.new()
-  buf:set_cluster_level(harfbuzz.Buffer.HB_BUFFER_CLUSTER_LEVEL_CHARACTERS)
-  buf:add_codepoints(codepoints)
-  harfbuzz.shape(font.harfbuzz.font,buf, { direction = lt_to_hb_dir[dir] })
-
-  -- Create new nodes from shaped text
-  if dir == 'TRT' then buf:reverse() end
-  local glyphs = buf:get_glyph_infos_and_positions()
-
-  for _, v in ipairs(glyphs) do
-    local n,k -- Node and (optional) Kerning
-    local char = font.backmap[v.codepoint]
-    if codepoints[v.cluster+1] == 0x20 then
-      assert(char == 0x20 or char == 0xa0, "Expected char to be 0x20 or 0xa0")
-      n = node.new("glue")
-      n.subtype = 0
-      n.width = font.parameters.space
-      n.stretch = font.parameters.space_stretch
-      n.shrink = font.parameters.space_shrink
-      new_head_slider.next = n
-    else
-      -- Create glyph node
-      n = node.new("glyph")
-      n.font = fontid
-      n.char = char
-      n.subtype = 1
-
-      -- Set offsets from Harfbuzz data
-      n.yoffset = upem_to_sp(v.y_offset, font)
-      n.xoffset = upem_to_sp(v.x_offset, font)
-      if dir == 'TRT' then n.xoffset = n.xoffset * -1 end
-
-      -- Adjust kerning if Harfbuzz’s x_advance does not match glyph width
-      local x_advance = upem_to_sp(v.x_advance, font)
-      if  math.abs(x_advance - n.width) > 1 then -- needs kerning
-        k = node.new("kern")
-        k.kern = (x_advance - n.width)
-      end
-
-      -- Insert glyph node into new list,
-      -- adjusting for direction and kerning.
-      if k then
-        if dir == 'TRT' then -- kerning goes before glyph
-          k.next = n
-          new_head_slider.next = k
-        else -- kerning goes after glyph
-          n.next = k
-          new_head_slider.next = n
-        end
-      else -- no kerning
-        new_head_slider.next = n
-      end
-    end
-    new_head_slider = node.slide(new_head_slider)
-  end
-
-  new_head_slider.next = new_tail
-  texio.write_nl("No. of nodes after shaping: "..node.length(new_head))
-  show_nodes(new_head, true)
-  return new_head
-end
-
--- Callback function
-local function show_and_process_nodes(head)
-  texio.write_nl("No. of nodes: "..node.length(head))
-  show_nodes(head)
-  return process_nodes(head)
-end
-
--- Register shaping callback
-callback.register("pre_linebreak_filter", show_and_process_nodes)
- - -
-
-
-generated by LDoc 1.4.5 -Last updated 2016-08-31 21:59:58 -
-
- - diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/ot_font_loader.lua.html b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/ot_font_loader.lua.html deleted file mode 100644 index 1abf52eebde..00000000000 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/ot_font_loader.lua.html +++ /dev/null @@ -1,139 +0,0 @@ - - - - - luaharfbuzz Documentation - - - - -
- -
- -
-
-
- - -
- - - - - - -
- -

ot_font_loader.lua

-
-local harfbuzz = require('harfbuzz')
-
--- Load OpenType font.
--- https://tug.org/TUGboat/tb33-1/tb103isambert.pdf
-local function read_font (name, size, fontid)
-  if size < 0 then
-    size = size * tex.sp("10pt") / -1000
-  end
-
-  -- Load file using fontloader.open
-  local f = fontloader.open (name)
-  local fonttable = fontloader.to_table(f)
-  fontloader.close(f)
-
-  local metrics = {
-    name = fonttable.fontname,
-    fullname = fonttable.fontname..fontid,
-    psname = fonttable.fontname,
-    type = "real",
-    filename = name,
-    format = string.match(string.lower(name), "otf$") and "opentype" or string.match(string.lower(name), "ttf$") and "truetype",
-    embedding = 'subset',
-    size = size,
-    designsize = fonttable.design_size*6553.6,
-    cidinfo = fonttable.cidinfo,
-    units_per_em = fonttable.units_per_em
-  }
-
-  -- Scaling for font metrics
-  local mag = size / fonttable.units_per_em
-
-  -- Find glyph for 0x20, and get width for spacing glue.
-  local space_glyph = fonttable.map.map[0x20]
-  local space_glyph_table = fonttable.glyphs[space_glyph]
-  local space_glyph_width = space_glyph_table.width * mag
-
-  metrics.parameters = {
-    slant = 0,
-    space = space_glyph_width,
-    space_stretch = 1.5 * space_glyph_width,
-    space_shrink = 0.5 * space_glyph_width,
-    x_height = fonttable.pfminfo.os2_xheight * mag,
-    quad = 1.0 * size,
-    extra_space = 0
-  }
-
-  -- Save backmap in TeX font, so we can get char code from glyph index
-  -- obtainded from Harfbuzz
-  metrics.backmap = fonttable.map.backmap
-
-  metrics.characters = { }
-  for char, glyph in pairs(fonttable.map.map) do
-    local glyph_table = fonttable.glyphs[glyph]
-    metrics.characters[char] = {
-      index = glyph,
-      width = glyph_table.width * mag,
-      name = glyph_table.name,
-    }
-    if glyph_table.boundingbox[4] then
-      metrics.characters[char].height = glyph_table.boundingbox[4] * mag
-    end
-    if glyph_table.boundingbox[2] then
-      metrics.characters[char].depth = -glyph_table.boundingbox[2] * mag
-    end
-  end
-
-  -- Store Harfbuzz data in the font to retrieve it in the shaping routine.
-  local face = harfbuzz.Face.new(name)
-  metrics.harfbuzz = {
-    face = face,
-    font = harfbuzz.Font.new(face)
-  }
-
-  return metrics
-end
-
--- Register OpenType font loader in define_font callback.
-callback.register('define_font', read_font, "font loader")
- - -
-
-
-generated by LDoc 1.4.5 -Last updated 2016-08-31 21:59:58 -
-
- - diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/package_path_searcher.lua.html b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/package_path_searcher.lua.html deleted file mode 100644 index 9ff317b2ea0..00000000000 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/examples/package_path_searcher.lua.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - luaharfbuzz Documentation - - - - -
- -
- -
-
-
- - -
- - - - - - -
- -

package_path_searcher.lua

-
--- Allows Lua modules to be loaded from package.path and package.cpath.
---
--- This behavior is overridden by default in LuaTeX. This module reverts the
--- packaging searching logic to use package.path and package.cpath first,
--- failing which it tries to use the overridden loading logic (which uses
--- kpse).
---
--- Package Loading References:
--- 1. http://www.lua.org/manual/5.2/manual.html#pdf-package.searchers
--- 2. LuaTeX Manual, Section 3.2, Lua behavior
-
-local make_loader = function(path, pos,loadfunc)
-  local default_loader = package.searchers[pos]
-  local loader = function(name)
-    local file = package.searchpath(name,path)
-    if not file then
-      local msg = "\n\t[lualoader] Search failed"
-      local ret = default_loader(name)
-      if type(ret) == "string" then
-        return msg ..ret
-        elseif type(ret) == "nil" then
-          return msg
-        else
-          return ret
-        end
-      end
-      local loader,err = loadfunc(file)
-      if not loader then
-        return "\n\t[lualoader] Loading error:\n\t"..err
-      end
-      return loader
-  end
-    package.searchers[pos] = loader
-end
-
-local binary_loader = function(file)
-  local base = file:match("/([^%.]+)%.[%w]+$")
-  local symbol = base:gsub("%.","_")
-  return package.loadlib(file, "luaopen_"..symbol)
-end
-
-make_loader(package.path,2,loadfile)
-make_loader(package.cpath,3, binary_loader)
- - -
-
-
-generated by LDoc 1.4.5 -Last updated 2016-08-31 21:59:58 -
-
- - diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/index.html b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/index.html index 443a4117ffc..d1aaf74c0fa 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/index.html +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/docs/index.html @@ -66,9 +66,9 @@

Info:

@@ -651,7 +651,7 @@
  • language: A Language object representing the language.
  • features: features to enable, specified as either of the following.
  • @@ -1774,7 +1774,7 @@

    Parameters:

    @@ -2822,7 +2822,7 @@
    generated by LDoc 1.4.6 -Last updated 2019-05-01 16:42:35 +Last updated 2019-07-31 18:39:39
    diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/fonts/TwitterColorEmoji-SVGinOT.ttf b/Build/source/texk/web2c/luatexdir/luaharfbuzz/fonts/TwitterColorEmoji-SVGinOT.ttf new file mode 100644 index 00000000000..a60d3ff3198 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luaharfbuzz/fonts/TwitterColorEmoji-SVGinOT.ttf differ diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.0.0-1.rockspec b/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.0.0-1.rockspec deleted file mode 100644 index c7cd2cc8c93..00000000000 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.0.0-1.rockspec +++ /dev/null @@ -1,51 +0,0 @@ -package = "luaharfbuzz" -version = "1.0.0-1" -source = { - url = "git://github.com/deepakjois/luaharfbuzz", - tag = "v1.0.0" -} -description = { - summary = "Lua bindings for the Harfbuzz text shaping library", - homepage = "https://github.com/deepakjois/luaharfbuzz", - license = "MIT", - maintainer = "Deepak Jois " -} -dependencies = { - "lua >= 5.2" -} -external_dependencies = { - HARFBUZZ = { - header = "harfbuzz/hb.h" - } -} -build = { - type = "builtin", - modules = { - harfbuzz = "src/harfbuzz.lua", - luaharfbuzz = { - incdirs = { - "$(HARFBUZZ_INCDIR)/harfbuzz" - }, - libdirs = { - "$(HARFBUZZ_LIBDIR)" - }, - libraries = { - "harfbuzz" - }, - sources = { - "src/luaharfbuzz/luaharfbuzz.c", - "src/luaharfbuzz/blob.c", - "src/luaharfbuzz/face.c", - "src/luaharfbuzz/font.c", - "src/luaharfbuzz/buffer.c", - "src/luaharfbuzz/feature.c", - "src/luaharfbuzz/tag.c", - "src/luaharfbuzz/unicode.c", - "src/luaharfbuzz/script.c", - "src/luaharfbuzz/direction.c", - "src/luaharfbuzz/language.c", - "src/luaharfbuzz/class_utils.c" - } - } - } -} diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.1.0-1.rockspec b/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.1.0-1.rockspec new file mode 100644 index 00000000000..17a84532b73 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-1.1.0-1.rockspec @@ -0,0 +1,46 @@ +package = "luaharfbuzz" +version = "1.1.0-1" +source = { + url = "git://github.com/ufytex/luaharfbuzz", + tag = "v1.1.0" +} +description = { + summary = "Lua bindings for the Harfbuzz text shaping library", + homepage = "https://github.com/ufytex/luaharfbuzz", + license = "MIT", + maintainer = "Deepak Jois " +} +dependencies = { + "lua >= 5.2" +} +build = { + type = "builtin", + modules = { + harfbuzz ="src/harfbuzz.lua", + luaharfbuzz= { + sources = { + "src/luaharfbuzz/luaharfbuzz.c", + "src/luaharfbuzz/blob.c", + "src/luaharfbuzz/face.c", + "src/luaharfbuzz/font.c", + "src/luaharfbuzz/buffer.c", + "src/luaharfbuzz/feature.c", + "src/luaharfbuzz/tag.c", + "src/luaharfbuzz/ot.c", + "src/luaharfbuzz/unicode.c", + "src/luaharfbuzz/script.c", + "src/luaharfbuzz/direction.c", + "src/luaharfbuzz/language.c", + "src/luaharfbuzz/class_utils.c" + }, + libraries = {"harfbuzz"}, + incdirs = {"$(HARFBUZZ_INCDIR)/harfbuzz"}, + libdirs = {"$(HARFBUZZ_LIBDIR)"} + } + } +} +external_dependencies = { + HARFBUZZ = { + header = "harfbuzz/hb.h" + } +} diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-scm-1.rockspec b/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-scm-1.rockspec index 108dde354fc..31ae2ab4fb7 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-scm-1.rockspec +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/luaharfbuzz-scm-1.rockspec @@ -1,3 +1,4 @@ +rockspec_format = "3.0" package = "luaharfbuzz" version = "scm-1" source = { @@ -7,7 +8,9 @@ description = { summary = "Lua bindings for the Harfbuzz text shaping library", homepage = "https://github.com/ufytex/luaharfbuzz", license = "MIT", - maintainer = "Deepak Jois " + maintainer = "Deepak Jois ", + issues_url = "https://github.com/ufytex/luaharfbuzz/issues", + labels = {"unicode", "fonts"} } dependencies = { "lua >= 5.2" diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/buffer_spec.lua b/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/buffer_spec.lua index 1950354eaf6..d0a7757e3bf 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/buffer_spec.lua +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/buffer_spec.lua @@ -167,6 +167,61 @@ describe("harfbuzz.Buffer", function() b:set_cluster_level(harfbuzz.Buffer.CLUSTER_LEVEL_CHARACTERS) assert.are_equal(harfbuzz.Buffer.CLUSTER_LEVEL_CHARACTERS, b:get_cluster_level()) end) + + it("can get the replacement glyph for invisible characters of the buffer", function() + local b = harfbuzz.Buffer.new() + assert.are_equal(0, b:get_invisible_glyph()) + end) + + it("can set the replacement glyph for invisible characters of the buffer", function() + local b = harfbuzz.Buffer.new() + b:set_invisible_glyph(3) + assert.are_equal(3, b:get_invisible_glyph()) + end) + + it("can get the replacement codepoint of the buffer", function() + local b = harfbuzz.Buffer.new() + assert.are_equal(0xFFFD, b:get_replacement_codepoint()) + end) + + it("can set the replacement codepoint of the buffer", function() + local b = harfbuzz.Buffer.new() + b:set_replacement_codepoint(0xFFFF) + assert.are_equal(0xFFFF, b:get_replacement_codepoint()) + b:add_utf8("\xFF") + local glyphs = b:get_glyphs() + assert.are_equal(1, #glyphs) + assert.are_equal(0xFFFF, glyphs[1].codepoint) + end) + + it("can get the flags of the buffer", function() + local b = harfbuzz.Buffer.new() + assert.are_equal(harfbuzz.Buffer.FLAG_DEFAULT, b:get_flags()) + end) + + it("can set the flags of the buffer", function() + local b = harfbuzz.Buffer.new() + b:set_flags(harfbuzz.Buffer.FLAG_DEFAULT | harfbuzz.Buffer.FLAG_BOT) + assert.are_equal(harfbuzz.Buffer.FLAG_DEFAULT | harfbuzz.Buffer.FLAG_BOT, b:get_flags()) + end) + + it("can clear the buffer", function() + local b = harfbuzz.Buffer.new() + b:add_utf8("abc") + b:set_flags(harfbuzz.Buffer.FLAG_DEFAULT | harfbuzz.Buffer.FLAG_BOT) + b:clear_contents() + assert.are_equal(0, b:get_length()) + assert.are_equal(harfbuzz.Buffer.FLAG_DEFAULT | harfbuzz.Buffer.FLAG_BOT, b:get_flags()) + end) + + it("can reset the buffer", function() + local b = harfbuzz.Buffer.new() + b:add_utf8("abc") + b:set_flags(harfbuzz.Buffer.FLAG_DEFAULT | harfbuzz.Buffer.FLAG_BOT) + b:reset() + assert.are_equal(0, b:get_length()) + assert.are_equal(harfbuzz.Buffer.FLAG_DEFAULT, b:get_flags()) + end) end) diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/harfbuzz_spec.lua b/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/harfbuzz_spec.lua index 966a1865faf..dfae07d8e65 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/harfbuzz_spec.lua +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/spec/harfbuzz_spec.lua @@ -140,12 +140,28 @@ describe("harfbuzz module", function() assert.are_same(layers,f:ot_color_glyph_get_layers(100)) end) - it("can check color layers", function() + it("can check PNG glyph support", function() local f = harfbuzz.Face.new('fonts/notocoloremoji-subset.ttf') assert.are_equal(false,face:ot_color_has_png()) assert.are_equal(true,f:ot_color_has_png()) end) + it("can check SVG glyph support", function() + local f = harfbuzz.Face.new('fonts/TwitterColorEmoji-SVGinOT.ttf') + assert.are_equal(false,face:ot_color_has_svg()) + assert.are_equal(true,f:ot_color_has_svg()) + end) + + it("can return glyph color png", function() + local f = harfbuzz.Face.new('fonts/TwitterColorEmoji-SVGinOT.ttf') + + assert.are_equal(nil,face:ot_color_glyph_get_svg(100)) + assert.are_equal(nil,f:ot_color_glyph_get_svg(0)) + assert.are_same(751,f:ot_color_glyph_get_svg(5):get_length()) + assert.are_same(804,f:ot_color_glyph_get_svg(6):get_length()) + assert.are_same("",f:ot_color_glyph_get_svg(5):get_data():sub(1, 38)) + end) + it("can return script tags", function() local t local tags = { @@ -320,6 +336,30 @@ describe("harfbuzz module", function() local f = harfbuzz.Feature.new(fs) assert.are_equal(fs, tostring(f)) end) + + it("has visible fields", function() + local f = harfbuzz.Feature.new('-kern') + print(getmetatable(f).__index) + assert.are_equal(tostring(f.tag), 'kern') + assert.are_equal(f.value, 0) + assert.are_equal(f.start, nil) + assert.are_equal(f._end, nil) + + f = harfbuzz.Feature.new('aalt[3:5]=4') + assert.are_equal(tostring(f.tag), 'aalt') + assert.are_equal(f.value, 4) + assert.are_equal(f.start, 3) + assert.are_equal(f._end, 5) + end) + + it("has editable fields", function() + local f = harfbuzz.Feature.new('-kern') + f.tag, f.value, f.start, f._end = harfbuzz.Tag.new"aalt", 4, 3, 5 + assert.are_equal(tostring(f), "aalt[3:5]=4") + + f.tag, f.value, f.start, f._end = harfbuzz.Tag.new"harf", 0, nil, nil + assert.are_equal(tostring(f), "-harf") + end) end) describe("harfbuzz.Tag", function() diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/harfbuzz.luadoc b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/harfbuzz.luadoc index 3b11636fae9..3a30a03c904 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/harfbuzz.luadoc +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/harfbuzz.luadoc @@ -1,8 +1,8 @@ ----------- -- Lua bindings to Harfbuzz. --- * [Wiki](http://github.com/deepakjois/luaharfbuzz/wiki) --- * [Source on Github](https://github.com/deepakjois/luaharfbuzz) --- * [API Coverage Status](https://github.com/deepakjois/luaharfbuzz/blob/master/status/done.txt) +-- * [Wiki](http://github.com/ufytex/luaharfbuzz/wiki) +-- * [Source on Github](https://github.com/ufytex/luaharfbuzz) +-- * [API Coverage Status](https://github.com/ufytex/luaharfbuzz/blob/master/status/done.txt) -- -- @author Deepak Jois <> -- @copyright 2016 @@ -23,7 +23,7 @@ -- * `script`: A `Script` object representing the script. -- * `language`: A `Language` object representing the language. -- * `features`: features to enable, specified as either of the following. --- - comma-separated list of features. See [feature string syntax reference](https://github.com/deepakjois/luaharfbuzz/wiki/Feature-Strings) +-- - comma-separated list of features. See [feature string syntax reference](https://github.com/ufytex/luaharfbuzz/wiki/Feature-Strings) -- - table of `Feature` objects -- @function shape @@ -291,7 +291,7 @@ -- @type Feature --- Wraps `hb_feature_from_string` --- @param feature_string See [feature string syntax reference](https://github.com/deepakjois/luaharfbuzz/wiki/Feature-Strings) +-- @param feature_string See [feature string syntax reference](https://github.com/ufytex/luaharfbuzz/wiki/Feature-Strings) -- @function Feature.new --- Wraps `hb_feature_to_string`. diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/buffer.c b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/buffer.c index 11f803693fd..4eb78ec7a9a 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/buffer.c +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/buffer.c @@ -1,27 +1,20 @@ #include "luaharfbuzz.h" #ifdef LuajitTeX -static void lua_len (lua_State *L, int i) { - switch (lua_type(L, i)) { - case LUA_TSTRING: - lua_pushnumber(L, (lua_Number)lua_objlen(L, i)); - break; - case LUA_TTABLE: - if (!luaL_callmeta(L, i, "__len")) - lua_pushnumber(L, (lua_Number)lua_objlen(L, i)); - break; - case LUA_TUSERDATA: - if (luaL_callmeta(L, i, "__len")) - break; - /* FALLTHROUGH */ - default: - luaL_error(L, "attempt to get length of a %s value", - lua_typename(L, lua_type(L, i))); - } + +static int lua_absindex (lua_State *L, int i) { + if (i < 0 && i > LUA_REGISTRYINDEX) + i += lua_gettop(L) + 1; + return i; +} +static int lua_geti (lua_State *L, int index, lua_Integer i) { + index = lua_absindex(L, index); + lua_pushinteger(L, i); + lua_gettable(L, index); + return lua_type(L, -1); } #endif - static int buffer_new(lua_State *L) { Buffer *b; @@ -59,6 +52,22 @@ static int buffer_set_direction(lua_State *L) { return 0; } +static int buffer_get_flags(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + lua_pushinteger(L, hb_buffer_get_flags(*b)); + return 1; +} + +static int buffer_set_flags(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + unsigned int l = luaL_checkinteger(L, 2); + + hb_buffer_set_flags(*b, l); + return 0; +} + static int buffer_get_language(lua_State *L) { Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); @@ -97,25 +106,56 @@ static int buffer_set_script(lua_State *L) { return 0; } +static int buffer_get_invisible_glyph(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + lua_pushinteger(L, hb_buffer_get_invisible_glyph(*b)); + return 1; +} + +static int buffer_set_invisible_glyph(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + hb_codepoint_t cp = (hb_codepoint_t) luaL_checkinteger(L, 2); + + hb_buffer_set_invisible_glyph(*b, cp); + return 0; +} + +static int buffer_get_replacement_codepoint(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + lua_pushinteger(L, hb_buffer_get_replacement_codepoint(*b)); + return 1; +} + +static int buffer_set_replacement_codepoint(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + hb_codepoint_t cp = (hb_codepoint_t) luaL_checkinteger(L, 2); + + hb_buffer_set_replacement_codepoint(*b, cp); + return 0; +} + static int buffer_add_codepoints(lua_State *L) { Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); unsigned int item_offset; int item_length; + int i; luaL_checktype(L, 2, LUA_TTABLE); item_offset = luaL_optinteger(L, 3, 0); item_length = luaL_optinteger(L, 4, -1); - lua_len (L, 2); - unsigned int n = luaL_checkinteger(L, -1); - lua_pop(L, 1); + int n = lua_rawlen(L, 2); hb_codepoint_t *text = (hb_codepoint_t *) malloc(n * sizeof(hb_codepoint_t)); - lua_pushnil(L); int i = 0; - while (lua_next(L, 2) != 0) { + for (i = 0; i != n; ++i) { + lua_geti(L, 2, i + 1); hb_codepoint_t c = (hb_codepoint_t) luaL_checkinteger(L, -1); - text[i++] = c; + text[i] = c; lua_pop(L, 1); } @@ -126,6 +166,20 @@ static int buffer_add_codepoints(lua_State *L) { return 0; } +static int buffer_clear_contents(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + hb_buffer_clear_contents(*b); + return 0; +} + +static int buffer_reset(lua_State *L) { + Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); + + hb_buffer_reset(*b); + return 0; +} + static int buffer_add_utf8(lua_State *L) { Buffer *b = (Buffer *)luaL_checkudata(L, 1, "harfbuzz.Buffer"); const char *text; @@ -238,14 +292,22 @@ static const struct luaL_Reg buffer_methods[] = { { "__gc", buffer_destroy }, { "add_utf8", buffer_add_utf8 }, { "add_codepoints", buffer_add_codepoints }, + { "clear_contents", buffer_clear_contents }, { "set_direction", buffer_set_direction }, { "get_direction", buffer_get_direction }, + { "set_flags", buffer_set_flags }, + { "get_flags", buffer_get_flags }, { "set_language", buffer_set_language }, { "get_language", buffer_get_language }, { "set_script", buffer_set_script }, { "get_script", buffer_get_script }, + { "set_invisible_glyph", buffer_set_invisible_glyph }, + { "get_invisible_glyph", buffer_get_invisible_glyph }, + { "set_replacement_codepoint", buffer_set_replacement_codepoint }, + { "get_replacement_codepoint", buffer_get_replacement_codepoint }, { "get_glyphs", buffer_get_glyphs }, { "guess_segment_properties", buffer_guess_segment_properties }, + { "reset", buffer_reset }, { "reverse", buffer_reverse }, { "get_length", buffer_get_length }, { "get_cluster_level", buffer_get_cluster_level }, @@ -264,6 +326,12 @@ static const struct luahb_constant_t buffer_constants[] = { { "CLUSTER_LEVEL_MONOTONE_CHARACTERS", HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS }, { "CLUSTER_LEVEL_CHARACTERS", HB_BUFFER_CLUSTER_LEVEL_CHARACTERS }, { "CLUSTER_LEVEL_DEFAULT", HB_BUFFER_CLUSTER_LEVEL_DEFAULT }, + { "FLAG_DEFAULT", HB_BUFFER_FLAG_DEFAULT }, + { "FLAG_BOT", HB_BUFFER_FLAG_BOT }, + { "FLAG_EOT", HB_BUFFER_FLAG_EOT }, + { "FLAG_PRESERVE_DEFAULT_IGNORABLES", HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES }, + { "FLAG_REMOVE_DEFAULT_IGNORABLES", HB_BUFFER_FLAG_REMOVE_DEFAULT_IGNORABLES }, + { "FLAG_DO_NOT_INSERT_DOTTED_CIRCLE", HB_BUFFER_FLAG_DO_NOT_INSERT_DOTTED_CIRCLE }, { "GLYPH_FLAG_UNSAFE_TO_BREAK", HB_GLYPH_FLAG_UNSAFE_TO_BREAK }, { "GLYPH_FLAG_DEFINED", HB_GLYPH_FLAG_DEFINED }, { NULL, 0 } diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/face.c b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/face.c index ddb05581fae..5538c704571 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/face.c +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/face.c @@ -398,6 +398,31 @@ static int face_ot_color_has_png(lua_State *L) { return 1; } +static int face_ot_color_has_svg(lua_State *L) { + Face *f = (Face *)luaL_checkudata(L, 1, "harfbuzz.Face"); + + lua_pushboolean(L, hb_ot_color_has_svg(*f)); + return 1; +} + +static int face_ot_color_glyph_get_svg(lua_State *L) { + Face *f = (Face *)luaL_checkudata(L, 1, "harfbuzz.Face"); + hb_codepoint_t gid = (hb_codepoint_t) luaL_checkinteger(L, 2); + hb_blob_t* blob = hb_ot_color_glyph_reference_svg(*f, gid); + + if (hb_blob_get_length(blob) != 0) { + Blob *b = (Blob *)lua_newuserdata(L, sizeof(*b)); + luaL_getmetatable(L, "harfbuzz.Blob"); + lua_setmetatable(L, -2); + + *b = blob; + } else { + lua_pushnil(L); + } + + return 1; +} + static int face_destroy(lua_State *L) { Face *f = (Face *)luaL_checkudata(L, 1, "harfbuzz.Face"); @@ -419,6 +444,8 @@ static const struct luaL_Reg face_methods[] = { { "ot_color_has_layers", face_ot_color_has_layers }, { "ot_color_glyph_get_layers", face_ot_color_glyph_get_layers }, { "ot_color_has_png", face_ot_color_has_png }, + { "ot_color_has_svg", face_ot_color_has_svg }, + { "ot_color_glyph_get_svg", face_ot_color_glyph_get_svg }, { "ot_layout_get_script_tags", face_ot_layout_get_script_tags }, { "ot_layout_get_language_tags", face_ot_layout_get_language_tags }, { "ot_layout_get_feature_tags", face_ot_layout_get_feature_tags }, diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/feature.c b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/feature.c index 1a3cf0a7815..d6cd1ec325b 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/feature.c +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/feature.c @@ -26,7 +26,63 @@ static int feature_to_string(lua_State *L) { return 1; } +static const char *feature_tag_ptr; +static const char *feature_value_ptr; +static const char *feature_start_ptr; +static const char *feature_end_ptr; + +static int feature_index(lua_State *L) { + Feature* f = (Feature *)luaL_checkudata(L, 1, "harfbuzz.Feature"); + const char *key = lua_tostring(L, 2); + + if (key == feature_tag_ptr) { + Tag *tag = (Tag *)lua_newuserdata(L, sizeof(*tag)); + luaL_getmetatable(L, "harfbuzz.Tag"); + lua_setmetatable(L, -2); + *tag = f->tag; + } else if (key == feature_value_ptr) { + lua_pushinteger(L, f->value); + } else if (key == feature_start_ptr) { + if (f->start == HB_FEATURE_GLOBAL_START) + lua_pushnil(L); + else + lua_pushinteger(L, f->start); + } else if (key == feature_end_ptr) { + if (f->end == HB_FEATURE_GLOBAL_END) + lua_pushnil(L); + else + lua_pushinteger(L, f->end); + } else { + lua_pushnil(L); + } + return 1; +} + +static int feature_newindex(lua_State *L) { + Feature* f = (Feature *)luaL_checkudata(L, 1, "harfbuzz.Feature"); + const char *key = lua_tostring(L, 2); + + if (key == feature_tag_ptr) { + f->tag = *(Tag *)luaL_checkudata(L, 3, "harfbuzz.Tag"); + } else if (key == feature_value_ptr) { + f->value = luaL_checkinteger(L, 3); + } else if (key == feature_start_ptr) { + if (lua_toboolean(L, 3)) + f->start = luaL_checkinteger(L, 3); + else + f->start = HB_FEATURE_GLOBAL_START; + } else if (key == feature_end_ptr) { + if (lua_toboolean(L, 3)) + f->end = luaL_checkinteger(L, 3); + else + f->end = HB_FEATURE_GLOBAL_END; + } + return 0; +} + static const struct luaL_Reg feature_methods[] = { + { "__index", feature_index }, + { "__newindex", feature_newindex }, { "__tostring", feature_to_string }, { NULL, NULL }, }; @@ -37,5 +93,18 @@ static const struct luaL_Reg feature_functions[] = { }; int register_feature(lua_State *L) { + lua_pushliteral(L, "tag"); + feature_tag_ptr = lua_tostring(L, -1); + (void) luaL_ref (L, LUA_REGISTRYINDEX); + lua_pushliteral(L, "value"); + feature_value_ptr = lua_tostring(L, -1); + (void) luaL_ref (L, LUA_REGISTRYINDEX); + lua_pushliteral(L, "start"); + feature_start_ptr = lua_tostring(L, -1); + (void) luaL_ref (L, LUA_REGISTRYINDEX); + lua_pushliteral(L, "_end"); /* _end instead of end to avoid Lua keyword */ + feature_end_ptr = lua_tostring(L, -1); + (void) luaL_ref (L, LUA_REGISTRYINDEX); + return register_class(L, "harfbuzz.Feature", feature_methods, feature_functions, NULL); } diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/font.c b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/font.c index 2c59ce55a67..c601673647e 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/font.c +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/font.c @@ -184,7 +184,7 @@ static int font_ot_color_glyph_get_png(lua_State *L) { luaL_getmetatable(L, "harfbuzz.Blob"); lua_setmetatable(L, -2); - *b = hb_ot_color_glyph_reference_png(*f, gid); + *b = blob; } else { lua_pushnil(L); } diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/luaharfbuzz.c b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/luaharfbuzz.c index c41a46bb7e9..ac7081f0183 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/luaharfbuzz.c +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/src/luaharfbuzz/luaharfbuzz.c @@ -1,30 +1,42 @@ #include "luaharfbuzz.h" +#ifdef LuajitTeX +static int lua_absindex (lua_State *L, int i) { + if (i < 0 && i > LUA_REGISTRYINDEX) + i += lua_gettop(L) + 1; + return i; +} +static int lua_geti (lua_State *L, int index, lua_Integer i) { + index = lua_absindex(L, index); + lua_pushinteger(L, i); + lua_gettable(L, index); + return lua_type(L, -1); +} +#endif int shape_full (lua_State *L) { - int i = 0; Font *font = (Font *)luaL_checkudata(L, 1, "harfbuzz.Font"); Buffer *buf = (Buffer *)luaL_checkudata(L, 2, "harfbuzz.Buffer"); + unsigned int i; luaL_checktype(L, 3, LUA_TTABLE); luaL_checktype(L, 4, LUA_TTABLE); unsigned int num_features = lua_rawlen(L, 3); Feature *features = (Feature *) malloc (num_features * sizeof(hb_feature_t)); - lua_pushnil(L); - while (lua_next(L, 3) != 0) { + for (i = 0; i != num_features; ++i) { + lua_geti(L, 3, i + 1); Feature* f = (Feature *)luaL_checkudata(L, -1, "harfbuzz.Feature"); - features[i++] = *f; + features[i] = *f; lua_pop(L, 1); } const char **shapers = NULL; size_t num_shapers = lua_rawlen(L, 4); if (num_shapers) { - i = 0; shapers = (const char**) calloc (num_shapers + 1, sizeof(char*)); - lua_pushnil(L); - while (lua_next(L, 4) != 0) { - shapers[i++] = luaL_checkstring(L, -1); + for (i = 0; i != num_shapers; ++i) { + lua_geti(L, 4, i + 1); + shapers[i] = luaL_checkstring(L, -1); lua_pop(L, 1); } } diff --git a/Build/source/texk/web2c/luatexdir/luaharfbuzz/status/full_api.txt b/Build/source/texk/web2c/luatexdir/luaharfbuzz/status/full_api.txt index d68c9b0f239..3b6728fcefb 100644 --- a/Build/source/texk/web2c/luatexdir/luaharfbuzz/status/full_api.txt +++ b/Build/source/texk/web2c/luatexdir/luaharfbuzz/status/full_api.txt @@ -1,4 +1,12 @@ +hb_aat_layout_feature_type_get_name_id +hb_aat_layout_feature_type_get_selector_infos +hb_aat_layout_get_feature_types +hb_aat_layout_has_positioning +hb_aat_layout_has_substitution +hb_aat_layout_has_tracking +hb_blob_copy_writable_or_fail hb_blob_create +hb_blob_create_from_file hb_blob_create_sub_blob hb_blob_destroy hb_blob_get_data @@ -17,10 +25,12 @@ hb_buffer_add_utf16 hb_buffer_add_utf32 hb_buffer_add_utf8 hb_buffer_allocation_successful +hb_buffer_append hb_buffer_clear_contents hb_buffer_create hb_buffer_deserialize_glyphs hb_buffer_destroy +hb_buffer_diff hb_buffer_get_cluster_level hb_buffer_get_content_type hb_buffer_get_direction @@ -28,6 +38,7 @@ hb_buffer_get_empty hb_buffer_get_flags hb_buffer_get_glyph_infos hb_buffer_get_glyph_positions +hb_buffer_get_invisible_glyph hb_buffer_get_language hb_buffer_get_length hb_buffer_get_replacement_codepoint @@ -51,6 +62,7 @@ hb_buffer_set_cluster_level hb_buffer_set_content_type hb_buffer_set_direction hb_buffer_set_flags +hb_buffer_set_invisible_glyph hb_buffer_set_language hb_buffer_set_length hb_buffer_set_message_func @@ -59,17 +71,25 @@ hb_buffer_set_script hb_buffer_set_segment_properties hb_buffer_set_unicode_funcs hb_buffer_set_user_data -hb_coretext_face_create -hb_coretext_face_get_cg_font -hb_coretext_font_get_ct_font +hb_color_get_alpha +hb_color_get_blue +hb_color_get_green +hb_color_get_red hb_direction_from_string hb_direction_to_string +hb_face_builder_add_table +hb_face_builder_create +hb_face_collect_unicodes +hb_face_collect_variation_selectors +hb_face_collect_variation_unicodes +hb_face_count hb_face_create hb_face_create_for_tables hb_face_destroy hb_face_get_empty hb_face_get_glyph_count hb_face_get_index +hb_face_get_table_tags hb_face_get_upem hb_face_get_user_data hb_face_is_immutable @@ -101,13 +121,16 @@ hb_font_funcs_set_glyph_extents_func hb_font_funcs_set_glyph_from_name_func hb_font_funcs_set_glyph_func hb_font_funcs_set_glyph_h_advance_func +hb_font_funcs_set_glyph_h_advances_func hb_font_funcs_set_glyph_h_kerning_func hb_font_funcs_set_glyph_h_origin_func hb_font_funcs_set_glyph_name_func hb_font_funcs_set_glyph_v_advance_func +hb_font_funcs_set_glyph_v_advances_func hb_font_funcs_set_glyph_v_kerning_func hb_font_funcs_set_glyph_v_origin_func hb_font_funcs_set_nominal_glyph_func +hb_font_funcs_set_nominal_glyphs_func hb_font_funcs_set_user_data hb_font_funcs_set_variation_glyph_func hb_font_get_empty @@ -115,29 +138,33 @@ hb_font_get_extents_for_direction hb_font_get_face hb_font_get_glyph hb_font_get_glyph_advance_for_direction +hb_font_get_glyph_advances_for_direction hb_font_get_glyph_contour_point hb_font_get_glyph_contour_point_for_origin hb_font_get_glyph_extents hb_font_get_glyph_extents_for_origin hb_font_get_glyph_from_name hb_font_get_glyph_h_advance +hb_font_get_glyph_h_advances hb_font_get_glyph_h_kerning hb_font_get_glyph_h_origin hb_font_get_glyph_kerning_for_direction hb_font_get_glyph_name hb_font_get_glyph_origin_for_direction hb_font_get_glyph_v_advance +hb_font_get_glyph_v_advances hb_font_get_glyph_v_kerning hb_font_get_glyph_v_origin hb_font_get_h_extents hb_font_get_nominal_glyph hb_font_get_parent hb_font_get_ppem +hb_font_get_ptem hb_font_get_scale hb_font_get_user_data -hb_font_get_v_extents hb_font_get_var_coords_normalized hb_font_get_variation_glyph +hb_font_get_v_extents hb_font_glyph_from_string hb_font_glyph_to_string hb_font_is_immutable @@ -148,6 +175,7 @@ hb_font_set_funcs hb_font_set_funcs_data hb_font_set_parent hb_font_set_ppem +hb_font_set_ptem hb_font_set_scale hb_font_set_user_data hb_font_set_var_coords_design @@ -157,6 +185,7 @@ hb_font_subtract_glyph_origin_for_direction hb_ft_face_create hb_ft_face_create_cached hb_ft_face_create_referenced +hb_ft_font_changed hb_ft_font_create hb_ft_font_create_referenced hb_ft_font_get_face @@ -167,15 +196,80 @@ hb_glib_blob_create hb_glib_get_unicode_funcs hb_glib_script_from_script hb_glib_script_to_script -hb_icu_get_unicode_funcs -hb_icu_script_from_script -hb_icu_script_to_script +hb_glyph_info_get_glyph_flags +hb_gobject_aat_layout_feature_selector_get_type +hb_gobject_aat_layout_feature_type_get_type +hb_gobject_blob_get_type +hb_gobject_buffer_cluster_level_get_type +hb_gobject_buffer_content_type_get_type +hb_gobject_buffer_diff_flags_get_type +hb_gobject_buffer_flags_get_type +hb_gobject_buffer_get_type +hb_gobject_buffer_serialize_flags_get_type +hb_gobject_buffer_serialize_format_get_type +hb_gobject_direction_get_type +hb_gobject_face_get_type +hb_gobject_feature_get_type +hb_gobject_font_funcs_get_type +hb_gobject_font_get_type +hb_gobject_glyph_flags_get_type +hb_gobject_glyph_info_get_type +hb_gobject_glyph_position_get_type +hb_gobject_map_get_type +hb_gobject_memory_mode_get_type +hb_gobject_ot_color_palette_flags_get_type +hb_gobject_ot_layout_glyph_class_get_type +hb_gobject_ot_math_constant_get_type +hb_gobject_ot_math_glyph_part_flags_get_type +hb_gobject_ot_math_glyph_part_get_type +hb_gobject_ot_math_glyph_variant_get_type +hb_gobject_ot_math_kern_get_type +hb_gobject_ot_var_axis_flags_get_type +hb_gobject_script_get_type +hb_gobject_segment_properties_get_type +hb_gobject_set_get_type +hb_gobject_shape_plan_get_type +hb_gobject_unicode_combining_class_get_type +hb_gobject_unicode_funcs_get_type +hb_gobject_unicode_general_category_get_type +hb_gobject_user_data_key_get_type +hb_graphite2_face_get_gr_face +hb_graphite2_font_get_gr_font hb_language_from_string hb_language_get_default hb_language_to_string +hb_map_allocation_successful +hb_map_clear +hb_map_create +hb_map_del +hb_map_destroy +hb_map_get +hb_map_get_empty +hb_map_get_population +hb_map_get_user_data +hb_map_has +hb_map_is_empty +hb_map_reference +hb_map_set +hb_map_set_user_data +hb_ot_color_glyph_get_layers +hb_ot_color_glyph_reference_png +hb_ot_color_glyph_reference_svg +hb_ot_color_has_layers +hb_ot_color_has_palettes +hb_ot_color_has_png +hb_ot_color_has_svg +hb_ot_color_palette_color_get_name_id +hb_ot_color_palette_get_colors +hb_ot_color_palette_get_count +hb_ot_color_palette_get_flags +hb_ot_color_palette_get_name_id hb_ot_font_set_funcs +hb_ot_layout_collect_features hb_ot_layout_collect_lookups +hb_ot_layout_feature_get_characters hb_ot_layout_feature_get_lookups +hb_ot_layout_feature_get_name_ids hb_ot_layout_feature_with_variations_get_lookups hb_ot_layout_get_attach_points hb_ot_layout_get_glyph_class @@ -191,16 +285,19 @@ hb_ot_layout_language_get_feature_tags hb_ot_layout_language_get_required_feature hb_ot_layout_language_get_required_feature_index hb_ot_layout_lookup_collect_glyphs +hb_ot_layout_lookups_substitute_closure hb_ot_layout_lookup_substitute_closure hb_ot_layout_lookup_would_substitute hb_ot_layout_script_find_language hb_ot_layout_script_get_language_tags +hb_ot_layout_script_select_language hb_ot_layout_table_choose_script hb_ot_layout_table_find_feature_variations hb_ot_layout_table_find_script hb_ot_layout_table_get_feature_tags hb_ot_layout_table_get_lookup_count hb_ot_layout_table_get_script_tags +hb_ot_layout_table_select_script hb_ot_math_get_constant hb_ot_math_get_glyph_assembly hb_ot_math_get_glyph_italics_correction @@ -210,16 +307,28 @@ hb_ot_math_get_glyph_variants hb_ot_math_get_min_connector_overlap hb_ot_math_has_data hb_ot_math_is_glyph_extended_shape +hb_ot_name_get_utf16 +hb_ot_name_get_utf32 +hb_ot_name_get_utf8 +hb_ot_name_list_names hb_ot_shape_glyphs_closure hb_ot_shape_plan_collect_lookups hb_ot_tag_from_language +hb_ot_tags_from_script +hb_ot_tags_from_script_and_language +hb_ot_tags_to_script_and_language hb_ot_tag_to_language hb_ot_tag_to_script -hb_ot_tags_from_script hb_ot_var_find_axis +hb_ot_var_find_axis_info hb_ot_var_get_axes hb_ot_var_get_axis_count +hb_ot_var_get_axis_infos +hb_ot_var_get_named_instance_count hb_ot_var_has_data +hb_ot_var_named_instance_get_design_coords +hb_ot_var_named_instance_get_postscript_name_id +hb_ot_var_named_instance_get_subfamily_name_id hb_ot_var_normalize_coords hb_ot_var_normalize_variations hb_script_from_iso15924_tag @@ -246,8 +355,11 @@ hb_set_intersect hb_set_invert hb_set_is_empty hb_set_is_equal +hb_set_is_subset hb_set_next hb_set_next_range +hb_set_previous +hb_set_previous_range hb_set_reference hb_set_set hb_set_set_user_data @@ -268,6 +380,20 @@ hb_shape_plan_get_shaper hb_shape_plan_get_user_data hb_shape_plan_reference hb_shape_plan_set_user_data +hb_subset +hb_subset_input_create_or_fail +hb_subset_input_destroy +hb_subset_input_drop_tables_set +hb_subset_input_get_desubroutinize +hb_subset_input_get_drop_hints +hb_subset_input_get_retain_gids +hb_subset_input_glyph_set +hb_subset_input_nameid_set +hb_subset_input_reference +hb_subset_input_set_desubroutinize +hb_subset_input_set_drop_hints +hb_subset_input_set_retain_gids +hb_subset_input_unicode_set hb_tag_from_string hb_tag_to_string hb_unicode_combining_class diff --git a/Build/source/texk/web2c/luatexdir/luamd5/md5lib.c b/Build/source/texk/web2c/luatexdir/luamd5/md5lib.c index dfbc0865a6b..d111a9142c6 100644 --- a/Build/source/texk/web2c/luatexdir/luamd5/md5lib.c +++ b/Build/source/texk/web2c/luatexdir/luamd5/md5lib.c @@ -162,7 +162,7 @@ static int decrypt (lua_State *L) { /* not now .. doesn't compile anyway -#include "../luapplib/util/utilmd5.h" +#include "../luapplib/src/util/utilmd5.h" static int pdfelib_md_5(lua_State * L) { @@ -194,7 +194,7 @@ int luaopen_md5(lua_State *L) { /* We could use a different file but this is as easy. */ -#include "../luapplib/util/utilsha.h" +#include "../luapplib/src/util/utilsha.h" static int sha2_256(lua_State * L) { @@ -202,7 +202,7 @@ static int sha2_256(lua_State * L) uint8_t result[SHA256_DIGEST_LENGTH]; size_t size = 0; const char *data = lua_tolstring(L,1,&size); - sha256(data,size,result); + sha256_digest(data,size,result,SHA_BYTES); lua_pushlstring(L,(const char *)result,SHA256_DIGEST_LENGTH); return 1; } @@ -215,7 +215,7 @@ static int sha2_384(lua_State * L) size_t size = 0; uint8_t result[SHA384_DIGEST_LENGTH]; const char *data = lua_tolstring(L,1,&size); - sha384(data,size,result); + sha384_digest(data,size,result,SHA_BYTES); lua_pushlstring(L,(const char *)result,SHA384_DIGEST_LENGTH); return 1; } @@ -228,7 +228,7 @@ static int sha2_512(lua_State * L) uint8_t result[SHA512_DIGEST_LENGTH]; size_t size = 0; const char *data = lua_tolstring(L,1,&size); - sha512(data,size,result); + sha512_digest(data,size,result,SHA_BYTES); lua_pushlstring(L,(const char *)result,SHA512_DIGEST_LENGTH); return 1; } diff --git a/Build/source/texk/web2c/luatexdir/luapeg/lpeg.c b/Build/source/texk/web2c/luatexdir/luapeg/lpeg.c index f424b598843..29b7707f2e1 100644 --- a/Build/source/texk/web2c/luatexdir/luapeg/lpeg.c +++ b/Build/source/texk/web2c/luatexdir/luapeg/lpeg.c @@ -394,7 +394,7 @@ static int removedyncap (lua_State *L, Capture *capture, */ /* luajit aarch64 */ /* https://github.com/LuaJIT/LuaJIT/pull/230#issuecomment-260205661 */ -/* We play safe on arm64 assuming a virtual address bits VA_BITS >47, +/* We play safe on arm64 assuming a virtual address bits VA_BITS >47,*/ /* even if a Linux kernel can be configured with VA_BITS < 47 */ /* and lightuserdata is ok then. Anyway, */ /* replacing lightuserdata with full userdata seems ok wrt performance. */ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/.gitattributes b/Build/source/texk/web2c/luatexdir/luapplib/.gitattributes new file mode 100644 index 00000000000..8d68adf9ae9 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/.gitattributes @@ -0,0 +1,10 @@ +*.c text=auto eol=lf +*.h text=auto eol=lf +Makefile text=auto eol=lf + +*.rst binary +*.png binary +*.jpg binary +*.css binary +*.html binary +*.js binary \ No newline at end of file diff --git a/Build/source/texk/web2c/luatexdir/luapplib/.gitignore b/Build/source/texk/web2c/luatexdir/luapplib/.gitignore new file mode 100644 index 00000000000..84d76071422 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/.gitignore @@ -0,0 +1,8 @@ +src/build/* +src/CMakeFiles/* +src/CMakeCache.txt +src/.vs/* +src/.cproject +src/.project +src/.settings +zlib/* \ No newline at end of file diff --git a/Build/source/texk/web2c/luatexdir/luapplib/.gitmodules b/Build/source/texk/web2c/luatexdir/luapplib/.gitmodules new file mode 100644 index 00000000000..4792336ecfc --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/.gitmodules @@ -0,0 +1,3 @@ +[submodule "zlib"] + path = zlib + url = git://github.com/madler/zlib.git diff --git a/Build/source/texk/web2c/luatexdir/luapplib/.travis.yml b/Build/source/texk/web2c/luatexdir/luapplib/.travis.yml new file mode 100644 index 00000000000..2f1c9a01cbc --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/.travis.yml @@ -0,0 +1,20 @@ +language: c + +script: + - mkdir build + - cd build + - cmake .. + - make -j 2 + - make -j 2 test + +matrix: + include: + - os: linux + compiler: clang + - os: linux + compiler: gcc + - os: osx + osx_image: xcode10.2 + allow_failures: + - os: osx + osx_image: xcode8 diff --git a/Build/source/texk/web2c/luatexdir/luapplib/CMakeLists.txt b/Build/source/texk/web2c/luatexdir/luapplib/CMakeLists.txt new file mode 100644 index 00000000000..8c2ea1e89ae --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/CMakeLists.txt @@ -0,0 +1,6 @@ +cmake_minimum_required(VERSION 3.5) + +add_subdirectory(zlib) +add_subdirectory(src) + +enable_testing() diff --git a/Build/source/texk/web2c/luatexdir/luapplib/Makefile.orig b/Build/source/texk/web2c/luatexdir/luapplib/Makefile.orig deleted file mode 100644 index 823c68f6bb9..00000000000 --- a/Build/source/texk/web2c/luatexdir/luapplib/Makefile.orig +++ /dev/null @@ -1,89 +0,0 @@ - -ifeq ($(ARCH),) - ARCH=x64 -endif - -UNAME:=$(shell uname) -ifeq ($(UNAME),Linux) - BUILDSUFFIX=_ux_$(ARCH) - SOEXT=.so - EXEEXT= - STATICCOPTS= -# SHAREDCOPTS=-fPIC - LFLAGS= - LIBS=-lm -else - BUILDSUFFIX=_win_$(ARCH) - SOEXT=.dll - EXEEXT=.exe - STATICCOPTS= -# SHAREDCOPTS=-DPPDLL - LFLAGS = -Wl,--output-def,$@.def,--out-implib,$@.a - LIBS= -endif - -CC=gcc -W=-Wall -Wunused -Wimplicit -Wreturn-type -Wdeclaration-after-statement -Wno-unknown-pragmas -Wmissing-prototypes -Wmissing-declarations -Wparentheses -Wswitch -Wtrigraphs -Wcast-qual -Wcast-align -Wwrite-strings -Wold-style-definition -Wpointer-arith -#W=-Wall -CFLAGS=$(W) -O2 - -OBJEXT=$(BUILDSUFFIX).o - -PPUTILS=utilmem utillog utilnumber utiliof utilmd5 utilsha utilcrypt -PPFILTERS=utilbasexx utilflate utillzw utilfpred -PPMODULES=ppheap pparray ppdict ppstream ppcrypt ppxref ppload - -OUTDIR=build -UTILSDIR=util - -PPSTATICUTILSOBJ=$(patsubst %, $(OUTDIR)/%$(OBJEXT), $(PPUTILS)) -PPSTATICFILTERSOBJ=$(patsubst %, $(OUTDIR)/%$(OBJEXT), $(PPFILTERS)) -PPSTATICOBJ=$(patsubst %, $(OUTDIR)/%$(OBJEXT), $(PPMODULES)) -PPSTATICLIB=$(OUTDIR)/libpp.static$(BUILDSUFFIX).a - -# dependencies -FLATEDIR=zlib -FLATELIB=$(FLATEDIR)/libz.static$(BUILDSUFFIX).a -PPSTATICDEPS=$(FLATELIB) - -# test programm -PPTEST1=$(OUTDIR)/pptest1$(EXEEXT) -PPTEST2=$(OUTDIR)/pptest2$(EXEEXT) -PPTEST3=$(OUTDIR)/pptest3$(EXEEXT) - -# includes -INC=-I $(UTILSDIR) -AUX=-I $(FLATEDIR) - -default: md $(PPSTATICLIB) $(PPTEST1) $(PPTEST2) $(PPTEST3) - -md: - @[ -d $(OUTDIR) ] || mkdir -p $(OUTDIR) - -$(PPSTATICOBJ): $(OUTDIR)/%$(OBJEXT): %.c %.h - $(CC) $(CFLAGS) $(STATICCOPTS) $(INC) -o $@ -c $< - -$(PPSTATICUTILSOBJ): $(OUTDIR)/%$(OBJEXT): $(UTILSDIR)/%.c $(UTILSDIR)/%.h - $(CC) $(CFLAGS) $(STATICCOPTS) $(INC) -o $@ -c $< - -$(PPSTATICFILTERSOBJ): $(OUTDIR)/%$(OBJEXT): $(UTILSDIR)/%.c $(UTILSDIR)/%.h - $(CC) $(CFLAGS) $(STATICCOPTS) $(INC) $(AUX) -o $@ -c $< - -$(PPSTATICLIB): $(PPSTATICOBJ) $(PPSTATICUTILSOBJ) $(PPSTATICFILTERSOBJ) - ar rcs $@ $^ - strip -N print_hex $@ - -$(PPTEST1): $(PPSTATICLIB) pptest1.c - $(CC) $(CFLAGS) $(STATICCOPTS) -o $(OUTDIR)/pptest1$(OBJEXT) -c pptest1.c - $(CC) -static-libgcc $(CFLAGS) -o $(PPTEST1) $(OUTDIR)/pptest1$(OBJEXT) $(PPSTATICLIB) $(PPSTATICDEPS) $(LIBS) - -$(PPTEST2): $(PPSTATICLIB) pptest2.c - $(CC) $(CFLAGS) $(STATICCOPTS) -o $(OUTDIR)/pptest2$(OBJEXT) -c pptest2.c - $(CC) -static-libgcc $(CFLAGS) -o $(PPTEST2) $(OUTDIR)/pptest2$(OBJEXT) $(PPSTATICLIB) $(PPSTATICDEPS) $(LIBS) - -$(PPTEST3): $(PPSTATICLIB) pptest3.c - $(CC) $(CFLAGS) $(STATICCOPTS) -I util -o $(OUTDIR)/pptest3$(OBJEXT) -c pptest3.c - $(CC) -static-libgcc $(CFLAGS) -o $(PPTEST3) $(OUTDIR)/pptest3$(OBJEXT) $(PPSTATICLIB) $(PPSTATICDEPS) $(LIBS) - -clean: - rm -f $(OUTDIR)/*$(OBJEXT) $(OUTDIR)/*.a $(OUTDIR)/*$(EXEEXT) diff --git a/Build/source/texk/web2c/luatexdir/luapplib/README.md b/Build/source/texk/web2c/luatexdir/luapplib/README.md new file mode 100644 index 00000000000..c684e9ed7ce --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/README.md @@ -0,0 +1,9 @@ +## pplib - pdf disassembling library for LuaTeX + +This is `plib` - PDF disassembling library for LuaTeX (http://luatex.org) + +The library has no LuaTeX dependency, it depends only on `zlib`. +However, `pplib` was tailor-made for LuaTeX and its functionals are +somewhat limited (eg. read-only PDF support). + +Author: Paweł Jackowski p.jackowski@gust.org.pl diff --git a/Build/source/texk/web2c/luatexdir/luapplib/azure-pipelines.yml b/Build/source/texk/web2c/luatexdir/luapplib/azure-pipelines.yml new file mode 100644 index 00000000000..365abe00716 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/azure-pipelines.yml @@ -0,0 +1,36 @@ +# C/C++ with GCC +# Build your C/C++ project with GCC using make. +# Add steps that publish test results, save build artifacts, deploy, and more: +# https://docs.microsoft.com/azure/devops/pipelines/apps/c-cpp/gcc + +trigger: +- master + +jobs: + +- job: Build + + strategy: + matrix: + linux: + imageName: "ubuntu-16.04" + mac: + imageName: "macos-10.13" + windows: + imageName: "vs2017-win2016" + maxParallel: 3 + + pool: + vmImage: $(imageName) + + steps: + - checkout: self + submodules: recursive + - task: CMake@1 + displayName: 'CMake ..' + inputs: + cmakeArgs: '..' + - task: CMake@1 + displayName: 'CMake --build . --config Debug' + inputs: + cmakeArgs: '--build . --config Debug' diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/Makefile b/Build/source/texk/web2c/luatexdir/luapplib/doc/Makefile new file mode 100644 index 00000000000..3ca7eeebf89 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/Makefile @@ -0,0 +1,20 @@ +# Minimal makefile for Sphinx documentation +# + +# You can set these variables from the command line. +SPHINXOPTS = +SPHINXBUILD = sphinx-build +SPHINXPROJ = pplib +SOURCEDIR = . +BUILDDIR = _build + +# Put it first so that "make" without argument is like "make help". +help: + @$(SPHINXBUILD) -M help "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) + +.PHONY: help Makefile + +# Catch-all target: route all unknown targets to Sphinx using the new +# "make mode" option. $(O) is meant as a shortcut for $(SPHINXOPTS). +%: Makefile + @$(SPHINXBUILD) -M $@ "$(SOURCEDIR)" "$(BUILDDIR)" $(SPHINXOPTS) $(O) \ No newline at end of file diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/environment.pickle b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/environment.pickle new file mode 100644 index 00000000000..c4d657a1115 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/environment.pickle differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-1.x.doctree b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-1.x.doctree new file mode 100644 index 00000000000..bd22032c659 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-1.x.doctree differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-2.x.doctree b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-2.x.doctree new file mode 100644 index 00000000000..d8c91b48bed Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi-2.x.doctree differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi.doctree b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi.doctree new file mode 100644 index 00000000000..9e432d80125 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppapi.doctree differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppcode.doctree b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppcode.doctree new file mode 100644 index 00000000000..a33b506208e Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppcode.doctree differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/pplib.doctree b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/pplib.doctree new file mode 100644 index 00000000000..0d5e84fe5a5 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/pplib.doctree differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppnew.doctree b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppnew.doctree new file mode 100644 index 00000000000..5c152d321a5 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/doctrees/ppnew.doctree differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/.buildinfo b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/.buildinfo new file mode 100644 index 00000000000..ec014001dee --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/.buildinfo @@ -0,0 +1,4 @@ +# Sphinx build info version 1 +# This file hashes the configuration used when building these files. When it is not found, a full rebuild will be done. +config: 5a0a9f8c8bb0798c3d499fe9e55f5963 +tags: 645f666f9bcd5a90fca523b33c5a78b7 diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-1.x.rst.txt b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-1.x.rst.txt new file mode 100644 index 00000000000..df661a7b82d --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-1.x.rst.txt @@ -0,0 +1,937 @@ + +``pplib`` 1.x +============= + +``pplib`` is a library for raw PDF access. It parses PDF documents and provides an interface to access document structures in C. + +C-API +===== + +Types +----- + +``pplib`` defines several C-types to represent PDF types: + +- ``ppint`` - signed integer (``int64_t``) +- ``ppnum`` - real number (double) +- ``ppname`` - PDF name +- ``ppstring`` - PDF string +- ``pparray`` - PDF array +- ``ppdict`` - PDF dict +- ``ppstream`` - PDF stream +- ``ppref`` - PDF indirect reference +- ``ppobj`` - a container of all above + +Among ``ppint`` and ``ppnum``, we also use ``ppuint`` - unsigned integer (machine word, alias to ``size_t``). + +Other API types: + +- ``ppdoc`` - PDF document +- ``ppxref`` - cross-references table +- ``ppcontext`` - ... later +- ``pprect`` - rectangle +- ``ppmatrix`` - matrix + +Integer, number, name and string are treated as simple types. +Names and strings are actually C-structures, but exposed to API as typedefs to ``const char *``. +Other types (array, dict, stream, reference, object container, xref, PDF) are C-structures, +and you operate it their pointers. So when you declare a simple type variable you say:: + + ppuint u; + ppnum n; + ppname name; + ppstring string; + ... + +And when you declare a compound type you operate on pointers:: + + ppobj *obj; + pparray *array; + ppdict *dict; + ppstream *stream; + ppref *ref; + ppdoc *pdf; + +Some of those C-types are defined in library header ``ppapi.h`` (complete types). Some others are incomplete +(eg. you can't say ``sizeof(ppdoc)`` or ``sizeof(ppxref)``). This is to avoid unnecesary dependencies in +the header. [At some points it's not clear to me what to hide and what to expose, will see.] The library itself +uses ``pplib.h`` but for auxilary applications including a standalone ``ppapi.h`` header should be enough. + +``pplib`` was designed having **read-only** PDF access in mind. Even if some structure is completelly exposed, +so that you can directly access its members, you should treat them as read-only. I don't make them ``const`` because +then all variable declarations would need to be ``const``, which is annoying, and I'd need some trickery in the library +internals to unconst. Besides, nothing is really const for C type casts. + +Object +------ + +A common container for all elementary PDF object types is ``ppobj`` structure. ``ppobj`` has a type identifier +(integer) and union of values:: + + struct ppobj { + ppobjtp type; + union { + ppint integer; + ppnum number; + ppname name; + ppstring string; + pparray *array; + ppdict *dict; + ppstream *stream; + ppref *ref; + void *any; + }; + }; + +Object type is one of constants (enum):: + + PPNONE + PPNULL + PPBOOL + PPINT + PPNUM + PPNAME + PPSTRING + PPARRAY + PPDICT + PPSTREAM + PPREF + +The type determines the structure member you're allowed to access:: + + ppobj *obj; + ... + switch (obj->type) + { + case PPNONE: // shouldn't actually happen, indicates some failure + break; + case PPNULL: // valid PDF null object, no value + break; + case PPBOOL: // do something with obj->integer (ppint), value 0 or 1 + break; + case PPINT: // do something with obj->integer (ppint) + break; + case PPNUM: // do something with obj->number (ppnum) + break; + case PPNAME: // do something with obj->name (ppname) + break; + case PPSTRING: // do something with obj->string (ppstring) + break; + case PPARRAY: // do something with obj->array (pparray *) + break; + case PPDICT: // do something with obj->dict (ppdict *) + break; + case PPSTREAM: // do something with obj->stream (ppstream *) + break; + case PPREF: // do something with obj->ref (ppref *) + break; + } + +More often then not you know exactly what type of object value is expected, in which case +you may use one of the following macros:: + + // returns 1 if o->type is PPNULL + int ppobj_get_null(o) \ + + // if o->type is PPBOOL, sets int v to 0 or 1 and returns 1, 0 otherwise + int ppobj_get_bool(o, v) + + // if o->type is PPINT, sets ppint v and returns 1, 0 otherwise + int ppobj_get_int(o, v) + + // if o->type is PPINT and >= 0, sets ppuint v and returns 1, 0 otherwise + int ppobj_get_uint(o, v) + + // if o->type is PPNUM or PPINT, sets ppnum v and returns 1, 0 otherwise + int ppobj_get_num(o, v) + + // if o->type is PPNAME returns the name, NULL otherwise + ppname ppobj_get_name(o) + + // if o->type is PPSTRING returns the string, NULL otherwise + ppstring ppobj_get_string(o) + + // if o->type is PPARRAY returns the array, NULL otherwise + pparray * ppobj_get_array(o) + + // if o->type is PPDICT returns the dict, NULL otherwise + ppdict * ppobj_get_dict(o) + + // if o->type is PPSTREAM returns the stream, NULL otherwise + ppstream * ppobj_get_stream(o) + + // if o->type is PPREF returns the reference, NULL otherwise + ppref * ppobj_get_ref(o) + +Note the coercion from integer to real number, but not reverse. In practise, whenever you expect a real number, +you should also handle integer (eg. '1' used instead of '1.0'). + +It is a common case that the object is given as an indirect reference, but what you actually +want is not the reference, but the object referred by it. Here is a helper for it:: + + // if o->type is PPREF, returns what the reference points, otherwise returns o + ppobj * ppobj_rget_obj(o) + +Also every ``ppobj_get_*`` macro has ``ppobj_rget_*`` counterpart that makes a check +for the expected type, but if the object is PPREF, it jumps to the target object. +So for example ``ppobj_rget_dict(obj)`` will return dict if ``obj`` is of type PPDICT +or if it is of type PPREF and ``obj->ref`` hosts an object of type PPDICT. + +Names +----- + +PDF names are represented as ``ppname``. +I find it convenient to have ``ppname`` type pretending ``const char *``. This allows to use ``ppname`` +in all C-style string functions like ``printf("%s", name)``. + +Be aware, however, that ``ppname`` is actually a C-structure. It is perfectly ok to cast ``ppname`` to ``const char *``:: + + ppname name; + ... + (const char *)name; + +But reverse is forbidden:: + + const char *cstr = "cstring"; + ... + (ppname)cstr; // expect segmentation fault soon + +For convenient use in C, names are ``'\0'`` terminated. But to get the length of name better always use +``ppname_size()`` macro. ``ppname`` object knows its size, don't use ``strlen()``:: + + size_t ppname_size(ppname name); // macro, returns length of name in bytes + +In current implementation names are not hashed anyhow, so name-to-name comparison is not smarter than ``memcmp()``. +Use macros:: + + int ppname_is(ppname name, "literal"); // to compare ppname with C-literal string + int ppname_eq(ppname name, ppname other); // to compare ppname with a different name + +If you'll use ``pplib`` to parse contents streams, you may need to distinguish names from operators +(more precisely executable names). Names in PDF are preceeded by '/', executable names aren't. In both +cases PDF parser will produce ``ppname`` but can be distingushed with:: + + int ppname_exec(ppname name); // returns non-zero if name is executable + +Names are kept in their raw form, with possible PDF specific escapes (in text below we call it **encoded** form). +Leading '/' is omitted, though. One may need a decoded name, with no PDF escapes. +A pair of functions provides a simple interface to switch between those two forms:: + + ppname ppname_decoded (ppname name); // returns decoded (unescaped) form of the name + ppname ppname_encoded (ppname name); // returns encoded (escaped) form of the name + +In pretty most cases PDF names contains only letters (no special characters, no escapes), so decoded and encoded forms are identical. +In that case both functions simply return the argument. It is ok to call ``ppname_decoded()`` on already decoded form +and ``ppname_encoded()`` on already encoded form. Both forms are produced by PDF objects parser, so accessing ``ppname`` alter ego +in whatever direction needs no extra decoding or allocation costs. + +String +------ + +PDF strings have the same internal construction as names, so most of names description above applies to strings as well. +``ppstring`` is a typedef of ``const char *``, roughly ``'\0'`` terminiated C-string. To get the size of the string:: + + size_t ppstring_size(ppstring string); // macro, returns the length of the string in bytes + +Strings are provided in their raw form, preserving PDF specific escapes, but with no +``()`` or ``<>`` delims. To distinguish plain strings from hex strings:: + + int ppstring_hex(ppstring string); // macro, returns non zero if hex string + +Or if you prefer:: + + switch (ppstring_type(string)) + { + case PPSTRING_PLAIN: // literal string, surrounded by ``(`` and ``)`` in PDF + break; + case PPSTRING_BASE16: // hex string, surrounded by ``<`` and ``>`` in PDF + break; + case PPSTRING_BASE85: // base85 string surrounded by ``<~`` and ``~>`` in PDF + break; + } + +The last is actually Postscript specific, not used in PDF, but I think it might appear in contents streams... +No matter how the string is given in PDF (plain or hex), here are two functions to +switch between encoded and decoded strings forms:: + + ppstring ppstring_decoded (ppstring string); // returns decoded string possibly with PDF escapes + ppstring ppstring_encoded (ppstring string); // returns encoded string with no PDF escapes + +For hex strings, encoded form contains hex digits, while decoded form contains arbitrary bytes (the result of hex decoding). +Plain strings usually contains printable ASCII characters, but they might contain any binary data. +As with names, objects parser produces both forms. The raw form with PDF escapes (or raw hex form) is considered the main one. +Eg. when you access ``obj->string`` you always get the encoded form. At any moment you can switch to its alter ego. + +No matter if the string is plain or hex, if its first two bytes (decoded) are UTF16 BOM, the string +is considered unicode. ``ppstring`` object *knows* it is unicode or not:: + + switch (ppstring_utf(string)) + { + case PPSTRING_UTF16LE: // unicode string, utf16le + break; + case PPSTRING_UTF16BE: // unicode string, utf16be + break; + default: // no unicode + } + +Or simply:: + + if (ppstring_utf(string) != 0) { + // handle unicode string + } + +If the string is unicode, BOM remains the part of the string -- ``pplib`` parser does not strip it. +Unicode or not, encoded or decoded, strings are always C-arrays of bytes and ``ppstring_size()`` +always returns the size in bytes. + +Array +----- + +PDF arrays are represented as ``pparray`` type, which is C-array of ``ppobj`` structures. +To get the size:: + + size_t pparray_size(pparray *array) // macro, returns the number of array items + +To get ``ppobj *`` at a given index:: + + ppobj * pparray_at(array, index) // macro, returns ppobj * (no index check) + ppobj * pparray_get(array, index) // macro, returns ppobj * or NULL (with index check) + ppobj * pparray_get_obj (pparray *array, size_t index); // function equiv to pparray_get() + +Iterating over array elements:: + + pparray *array; + size_t index, size; + ppobj *obj; + for (size = pparray_size(array), pparray_first(array, index, obj); index < size; pparray_next(index, obj)) + { + // do something with index and obj + } + +There is no magic first/next macros, just iteration over pointers. One could also use something like:: + + for (index = 0, size = array->size; index < size; ++index) + { + obj = pparray_at(array, index); + // do something with index and obj + } + +When getting values from array and expecting a result of known type, use one of the following:: + + int pparray_get_bool (pparray *array, size_t index, int *v); // get boolean value + int pparray_get_int (pparray *array, size_t index, ppint *v); // get ppint value + int pparray_get_uint (pparray *array, size_t index, ppuint *v); // get ppuint value + int pparray_get_num (pparray *array, size_t index, ppnum *v); // get ppnum value + ppname pparray_get_name (pparray *array, size_t index); // get ppname value + ppstring pparray_get_string (pparray *array, size_t index); // get ppstring value + pparray * pparray_get_array (pparray *array, size_t index); // get pparray * value + ppdict * pparray_get_dict (pparray *array, size_t index); // get ppdict * value + ppref * pparray_get_ref (pparray *array, size_t index); // get ppref * value + +As with ``ppobj_get_*`` suite, numeric types getters set the value of a given type and returns 1, if the type matches. +Otherwise sets nothing and returns 0. Other getters return the value if the type matches, or NULL. + +Every function from ``pparray_get_*`` suite have its ``pparray_rget_*`` counterpart that +that dereferences indirect objects (as explained for ``ppobj_rget_*`` getters). Note that +there is no ``pparray_get_stream()`` function, as streams in PDF are always indirect. +To get the stream from array use:: + + ppstream * pparray_rget_stream (pparray *array, size_t index); + +Dict +---- + +PDF dicts are represented as ``ppdict`` structure, which is C-array of ``ppobj`` with parallel +C-array of ``ppname`` pointers. To get the size of a dict:: + + size_t ppdict_size(ppdict *dict) // macro, returns the number of key-val pairs + +To get the value at a given index (integer):: + + ppobj * ppdict_at(ppdict *dict, index) // macro, no index check + +To get the name (key) at a given index:: + + ppname ppdict_key(ppdict *dict, index) // macro, no index check + +To iterate over dict key-val pairs:: + + ppdict *dict; + ppname *pkey; + ppobj *obj; + + for (ppdict_first(dict, pkey, obj); *pkey != NULL; ppdict_next(pkey, obj)) + { + // do something with *pkey and obj + } + +There is no magic in first/next macros, just iteration through keys and values lists pointers. +For convenient iteration, a list of keys is terminated with NULL, so in the code above ``*pkey != NULL`` +is used as the loop condition. One may also iterate via indices:: + + ppdict *dict; + size_t index, size; + ppname key; + ppobj *obj; + for (index = 0, size = ppdict_size(dict); index < size; ++index) + { + key = ppdict_key(dict, index); + obj = ppdict_at(dict, index); + // do something with key and obj + } + +To get the object associated with a given name, use one of the following:: + + ppobj * ppdict_get_obj (ppdict *dict, const char *name); + int ppdict_get_bool (ppdict *dict, const char *name, int *v); + int ppdict_get_int (ppdict *dict, const char *name, ppint *v); + int ppdict_get_uint (ppdict *dict, const char *name, ppuint *v); + int ppdict_get_num (ppdict *dict, const char *name, ppnum *v); + ppname ppdict_get_name (ppdict *dict, const char *name); + ppstring ppdict_get_string (ppdict *dict, const char *name); + pparray * ppdict_get_array (ppdict *dict, const char *name); + ppdict * ppdict_get_dict (ppdict *dict, const char *name); + ppref * ppdict_get_ref (ppdict *dict, const char *name); + +Note that all getters accepts ``const char *`` as key, so it is ok to say:: + + ppdict_rget_dict(dict, "Resources"); + +as well as:: + + ppdic_rget_dict(dict, name); // ppname name + +Every ``ppdict_get_*`` getter has ``ppdict_rget_*`` counterpart that dereferences +indirect objects if necessary. Note that there is no ``ppdict_get_stream()`` function, +but there is:: + + ppstream * ppdict_rget_stream (ppdict *dict, const char *name); + +So far dicts comes with no names mapping, so by-name dict accessors perform a linear search +through the keys list. PDF dicts are usually small, so it is fast enough. +Building names lookup for every dict in PDF makes no sense I think, as ``pplib`` applications +will query just several dicts I guess.. However, some apps may extensively query +resources, which may refer to hundreds of objects (eg. images). So some mapping for dicts +is still considered. + +Stream +------ + +PDF streams are represented as ``ppstream`` objects. To get the stream dict:: + + ppdict * ppstream_dict(ppstream *stream) // macro + +To read the stream data:: + + uint8_t * ppstream_first (ppstream *stream, size_t *size, int decode); + uint8_t * ppstream_next (ppstream *stream, size_t *size); + void ppstream_done (ppstream *stream); + +Both ``first` and ``next`` functions return a chunk of stream data and sets the ``size`` of the chunk. +``decode`` parameter tell the reader to decompress the stream (1) or return raw (0). A call to ``ppstream_next()`` +must be preceeded by ``ppstream_first()``. Once you're done with the stream, you have to call ``ppstream_done()``, +no matter if the stream has been read to the end or not. The stream data iterator in use:: + + uint8_t *data; + size_t size; + ppstream *stream; + int decode = 1; // 1 - get decompressed, 0 - get raw + + for (data = ppstream_first(stream, &size, decode); data != NULL; data = ppstream_next(stream, &size)) + { + // do something with data and its size + } + ppstream_done(stream); + +Every subsequent iterator call invalidates the previous reader output, so you have to utilize the returned chunk +of data just after you ot that. So the following is wrong:: + + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_next(stream, &size); + data3 = ppstream_next(stream, &size); + some_output(data1, size); + some_output(data2, size); + +The reader calls usually return the same pointer to internal buffer, just filled with a different data. +``pplib`` allocates reasonably large buffer and fills that buffer on subsequent calls to the reader. + +If the source stream has no compression, using both ``decode == 1`` and ``decode == 0`` should give the same result. +You can check if the stream is actually compressed with:: + + ppstream_compressed(stream) // macro, returns non zero if /Filter is present + +It might be necessary to load the entire stream data at once:: + + uint8_t * ppstream_all (ppstream *stream, size_t *size, int decode); + +If the initial buffer size is insufficient, it grows until the entire stream data is loaded. You must call +``ppstream_done(stream)`` after using returned data. + +``ppstream_done()`` doesn't invalidate the stream object, it just closes its internal reader. +The stream itself remains a valid object (eg. one can read it again if necessary), +but the reader buffer is released. It is actually not freed but kept for future the reuse with that on some other stream, +but you still need to mark it ready for reuse to avoid allocating a separate buffer for every stream you're going to read. + +Stream data readers will return ``NULL`` if you haven't close the previous reader process with ``ppstream_done()``. All below is wrong:: + + data1 = ppstream_all(stream, &size, 1); + data2 = ppstream_all(stream, &size, 1); // data2 == NULL + // or + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_first(stream, &size, 1); // data2 == NULL + // or + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_all(stream, &size, 1); // data2 == NULL + +To avoid unnecessary dependencies, ``pplib`` does not support image filters (``/DCT``, ``/JPX``, ``/JBIG``, ``/CCITT``). +But it is ok to read the stream with ``decode`` set to 1 on such streams. ``pplib`` assumes that the image is the +final/target stream form and just returns it as-is. Eg. in the case of JPEG (``/DCT`` filtered) image both calls should +give the same results:: + + ppstream_all(jpegstream, &jpegsize, 0); // don't decode, return what's there + ppstream_all(jpegstream, &jpegsize, 1); // decode but found image filter, effectively the same + +A bit more about streams memory. As mentioned, ``pplib`` allocates buffers for stream readers. After ``ppstream_done()``, +the stream no longer *owns* the buffer space. But the buffer may remain allocated, to be reused with future readers. +``pplib`` keeps a pool of several buffers. This means, that when you use stream readers, ``pplib`` eats +some memory (1MB or so) that is not freed, even if no streams are used. And even if you free all objects. +If you suffer from this, you can optionally use a pair of functions:: + + void ppstream_init_buffers (void); + void ppstream_free_buffers (void); + +The first initializes buffers pool, unless done so far. Currently ``pplib`` cares of it before opening every stream reader, +so it is not obligatory. The second frees a pool of buffers. The intended use is to call ``ppstream_init_buffers()`` once +as kind of library initializer and to call ``ppstream_free_buffers()`` once, as the library finalizer. + +Filters +------- + +In version v1.00 (20190916) ``ppstream`` API has been extended with filters information. +``ppstream`` knows its filter(s) and keps it as ``stream->filter``:: + + // ppstream *stream; + ppstream_filter *info = &stream->filter; + +``ppstream_filter`` is the following structure:: + + typedef struct { + ppstreamtp *filters; // c-array of filter identifiers (enum integers) + ppdict **params; // c-array of ppdict pointers + size_t count; // number of filters, length of the arrays (typically 1) + } ppstream_filter; + +If ``count > 0`` then ``filters`` member is not NULL. Filters array keeps integer constants:: + + PPSTREAM_BASE16 /* /ASCIIHexDecode */ + PPSTREAM_BASE85 /* /ASCII85Decode */ + PPSTREAM_RUNLENGTH /* /RunLengthDecode */ + PPSTREAM_FLATE /* /FlateDecode */ + PPSTREAM_LZW /* /LZWDecode */ + PPSTREAM_CCITT /* /CCITTFaxDecode */ + PPSTREAM_DCT /* /DCTDecode */ + PPSTREAM_JBIG2 /* /JBIG2Decode */ + PPSTREAM_JPX /* /JPXDecode */ + PPSTREAM_CRYPT /* /Crypt */ + +Params array keeps corresponding filter parameters (``/DecodeParms``) if present. ``params`` member is not NULL +if ``count > 0`` and the stream dict has ``/DecodeParms`` entry. Even if ``params`` is there, +for every N-th filter, ``params[N]`` may be NULL (corresponding to PDF ``null``). + +``stream->filter`` keeps the source stream filter information, which may not correspond to the result of stream readers +(``ppstream_first()``, ``ppstream_next()``, ``ppstream_all()``). The get the filters info relevant to the result from readers:: + + void ppstream_filter_info (ppstream *stream, ppstream_filter *info, int decode); + +The function fills ``ppstream_filter`` structure according to the expected result from stream readers (example 3 shows +how to use it to reconstruct ``/Filter`` and ``/DecodeParms`` when copying the stream to some other PDF). + +To convert filter identifier (``ppstreamtp``) to a corresponding PDF filter name:: + + const char * ppstream_filter_name[]; + +To covert ``ppname`` to filter identifier:: + + int ppstream_filter_type (ppname filtername, ppstreamtp *filtertype); + // returns 1 and sets filtertype if filtername is the proper filter name + +Additional information about the stream can be fetched from macros:: + + ppstream_compressed(stream) /* stream->flags & (PPSTREAM_FILTER|PPSTREAM_IMAGE) */ + ppstream_filtered(stream) /* stream->flags & PPSTREAM_FILTER */ + ppstream_image(stream) /* stream->flags * PPSTREAM_IMAGE */ + +``stream->flags`` is a binary sum of the following:: + + PPSTREAM_FILTER /* set iff the stream filters list has one of: BASE16, BASE85, RUNLENGTH, FLATE, LZW */ + PPSTREAM_IMAGE /* set iff the stream filters list has one of: CCITT, DCT, JBIG2, JPX */ + PPSTREAM_ENCRYPTED /* set iff the stream is encrypted */ + PPSTREAM_ENCRYPTED_OWN /* set iff the stream has own CRYPT filter */ + +Note that ``PPSTREAM_COMPRESSED`` is not there any longer, use ``ppstream_compressed()`` instead. +And there is some more, see ``ppapi.h``. + +Ref +--- + +Indirect objects are represented as ``ppref`` structure. To get the object that the +reference refers to:: + + ppobj * ppref_obj(ppref *ref) // macro + +``ppref`` structure also keeps the reference number and version, a pointer to cross reference table it belongs +to and others, but I guess you won't need anything but the referenced object. ``pplib`` parser resolves references +on-fly. So if there is a dict with indirect objects:: + + << + /Type /Page + /Resources 123 0 R + ... + >> + +the parser will produce ``ppdict`` with ``Resources`` key pointing the proper ``ppref *`` value. +If you need more, access ``ppref`` members:: + + struct ppref { + ppobj object; // target object + ppuint number, version; // identifiers + size_t offset; // file offset (useless for you, may be zero for compressed objects) + ppuint length; // the length of the original object data + ppxref *xref; // cross reference table it belongs to + }; + + +XRef +---- + +Cross reference table is exposed as ``ppxref`` (incomplete type, you can only oprate on its pointer). +To get top document xref:: + + ppxref * ppdoc_xref (ppdoc *pdf); + +To get previous (older) xref:: + + ppxref * ppxref_prev (ppxref *xref); + +To find an object of a given refnumber:: + + ppref * ppxref_find (ppxref *xref, ppuint refnumber); + +[Note: since pplib v0.98 in case of documents with incremental update, ``ppxref_find()`` returns +the newest available version of a given object rather than the object in a given body.] + +PDF +--- + +PDF document is represented as ``ppdoc`` structure (incomplete type, you can only operate on its pointer). +To load a document from file:: + + ppdoc * ppdoc_load (const char *filename); + +To load a document from memory data:: + + ppdoc * ppdoc_mem (const void *data, size_t size); + +The data is assumed to be a buffer allocated with ``malloc`` - it is freed when destroying ``ppdoc``. + +Both loaders returns ``NULL`` on failure. + +To free ``ppdoc`` and all objects it refers to:: + + void ppdoc_free (ppdoc *pdf); + +So far we haven't mention about any explicit object reclaimers. There are no dedicated ``free`` functions +for other objects. You don't allocate or free objects yourself. ``ppdoc`` object is an owner of all +beings it refers to. It also means that every object described so far is alive as long as the containing +``ppdoc`` is alive. + +To access main PDF dicts:: + + ppdict * ppdoc_trailer(ppdoc *pdf); // returns top xref trailer dict + ppdict * ppdoc_catalog(ppdoc *pdf); // returns catalog referred from the trailer + ppdict * ppdoc_info(ppdoc *pdf); // returns info dict referred from the trailer + +To get the PDF version:: + + const char * ppdoc_version_string (ppdoc *pdf); // version string + int ppdoc_version_number (ppdoc *pdf, int *minor); // minor and major numbers + +To get the file size of the source PDF document:: + + size_t ppdoc_file_size (ppdoc *pdf); + +To get the number of objects in all xrefs:: + + ppuint ppdoc_objects (ppdoc *pdf); + +To get the approx usage of memory:: + + size_t ppdoc_memory (ppdoc *pdf, size_t *waste); + +Encryption +---------- + +``pplib`` handles encrypted (password protected) documents. If a document is encrypted, most of strings and streams are ciphered. +In that form they are unreadable and rather useless, you can't even rewrite such strings/streams as-is to a different PDF output. +It is a common practise to *protect* documents with an empty password. Such documents remain readable in Acrobat (just opens them without prompting +for a password), but some features (eg. printing) may restricted by the application. + +When ``pplib`` detects encryption, it follows Acrobat approach and first tries an empty password. If it succeeds, ``pplib`` proceeeds normally, providing +an access to decrypted strings and streams, as if they weren't ciphered. If the document is protected with non-empty password, ``pplib`` gives +a way to provide a password and proceed. Until you provide a password, ``ppdoc`` object returned by ``ppdoc_load()`` function has all object wntries +set to ``null``. + +After loading a document you should check encryption status with:: + + ppcrypt_status ppdoc_crypt_status (ppdoc *pdf); + +``ppcrypt_status`` (integer) may have the following values: + + ``PPCRYPT_NONE`` - no encryption, go ahead + ``PPCRYPT_DONE`` - encryption present but password succeeded, go ahead + ``PPCRYPT_PASS`` - encryption present, need non-empty password + ``PPCRYPT_FAIL`` - invalid or unsupported encryption (eg. undocumented in pdf spec) + +If a password is needed, you can provide one with:: + + ppcrypt_status ppdoc_crypt_pass (ppdoc *pdf, const void *userpass, size_t userpasslength, + const void *ownerpass, size_t ownerpasslength); + +Well, yes, there are actually two passwords in encrypted documents. Relation between them is obscure to me, but enough +to know that having one of them is enough to decrypt the document. If you know the password, you probably mean +``userpass``, in which case you should put ``NULL`` as ``ownerpass``. The function returns ``PPCRYPT_DONE`` if the password +succeeds and the previous status otherwise. Your custom loader function may look like that:: + + ppdoc *pdf; + pdf = ppdoc_load("file.pdf"); + if (pdf == NULL) + return NULL; + switch (ppdoc_crypt_status(pdf)) + { + case PPCRYPT_NONE: + case PPCRYPT_DONE: + return pdf; + case PPCRYPT_PASS: + if (ppdoc_crypt_pass(pdf, "dummy", 5, NULL, 0) == PPCRYPT_DONE || + ppdoc_crypt_pass(pdf, NULL, 0, "dummy", 5) == PPCRYPT_DONE) + return pdf; + printf("sorry, password needed\n"); + ppdoc_free(pdf); + return NULL; + case PPCRYPT_FAIL: + printf("sorry, encryption failed\n"); + ppdoc_free(pdf); + return NULL; + } + +[If you get ``PPCRYPT_FAIL`` it might mean *I failed*, so treat as a bug.] + +If you'd like to know what permissions are given/restricted to encrypted document:: + + ppint ppdoc_permissions (ppdoc *pdf); + +Returned value can be queried with the following binary flags (you can verify with Acrobat *File -> Properties -> Security* tab):: + + PPDOC_ALLOW_PRINT // printing + PPDOC_ALLOW_MODIFY // filling form fields, signing, creating template pages + PPDOC_ALLOW_COPY // copying, copying for accessibility + PPDOC_ALLOW_ANNOTS // filling form fields, copying, signing + PPDOC_ALLOW_EXTRACT // contents copying for accessibility + PPDOC_ALLOW_ASSEMBLY // (no effect) + PPDOC_ALLOW_PRINT_HIRES // (no effect) + +``pplib`` does absolutelly nothing with permissions, it cares only to decrypt the document. As mentioned, encryption applies to strings +and streams. ``pplib`` decrypt strings when parsing document objects, so the result you get is *normal* (not ciphered). +Streams are decrypted whenever you access them. Even if you ask for a raw stream data, you'll get a raw (compressed) stream, but decrypted. +So except the check to ``ppdoc_crypt_status()``, you shouldn't bother about encryption. + +In encrypted documents most of streams are encrypted. To check if a given stream is encrypted:: + + ppstream_encrypted(stream) // macro, returns non-zero if encrypted + +Encryption is independent from compression, don't confuse with ``ppstream_compressed()`` + +Pages +----- + +Several helpers to deal with pages. To get the number of pages:: + + ppuint ppdoc_page_count (ppdoc *pdf); + +To access the root pages tree node:: + + ppref * ppdoc_pages(ppdoc *pdf); + +To get the page reference at a given index:: + + ppref * ppdoc_page (ppdoc *pdf, ppuint index); + +``index`` is a page number. First page has number 1. For index out of bounds ``ppdoc_page()`` returns NULL. +Iterating over pages using index from 1 to ``ppdoc_page_count()`` and calling ``ppdoc_page()`` on each iteration +would be suboptimal. Here is a dedicted iterator for this:: + + ppref * ppdoc_first_page (ppdoc *pdf); + ppref * ppdoc_next_page (ppdoc *pdf); + +The iterator in use:: + + ppdoc *pdf; + ppref *ref; + ppdict *dict; + int pageno; + + pdf = ppdoc_load("file.pdf"); + for (ref = ppdoc_first_page(pdf), pageno = 1; ref != NULL; ref = ppdoc_next_page(pdf), ++pageno) + { + dict = ppref_obj(obj)->dict; // take for granted it is a dict + // do something with the page dict + } + +Functions related to pages return ``ppref *`` ensured to contain dict object, so you don't need sanity +type checks here. + +Contents +-------- + +PDF page contents can be given as a stream or array of streams. Here is a convenience iterator over page +contents streams:: + + ppstream * ppcontents_first (ppdict *dict); + ppstream * ppcontents_next (ppdict *dict, ppstream *stream); + +A complete example of contents stream parser use is given below (example 2). +But before we get there, we need to introduce ``ppcontext`` object. Conceptually, +``ppcontext`` is an owner (memory handler) of objects created on demand (beyond the ``ppdoc``). +So far used only with contents stream parser, which might produce quite some data that we want +to release just after used. To create a new context:: + + pcontext * ppcontext_new (void); + +It initializes a new context and its internal memory heap, taking about 64kB on start. After that, +the context is ready to produce objects (contents parsing functions below). Once objects produced +from a given context are no longer needed:: + + void ppcontext_done (ppcontext *context); + +It restores the context to its initial state, as after ``ppcontext_new()``. It means that the context +is ready to produce another bunch of beings (in the example below, all objects from the next page contents). +Once the context is not needed anymore:: + + void ppcontext_free (ppcontext *context); + +Now, contents stream parser functions take the context as an argument. Iterator form of contents stream parser +that allows to process the contents operator by operator:: + + ppobj * ppcontents_first_op (ppcontext *context, ppstream *stream, size_t *psize, ppname *pname); + ppobj * ppcontents_next_op (ppcontext *context, ppstream *stream, size_t *psize, ppname *pname); + +Returned ``ppobj *`` is a pointer to operands list. ``*psize`` is the number of operands on stack. +The operator itself is stored as ``*pname``. + +To parse the entire contents stream at once with no stop at every operator:: + + ppobj * ppcontents_parse (ppcontext *context, ppstream *stream, size_t *psize); + +Returns probably quite long list of all parsed objects (operands and operatos) in one piece. +The number of objects is stored to ``*psize``. + +[Contents may contain so called inline images, that breaks a simple scheme of operands / operator syntax:: + + BI ID EI + +Contents parser treats this genuine triplet as a single piece, producing two operands (dict and string) +followed by ``EI`` operator name.] + +Boxes +----- + +Boxes (rectangles) in PDF are roughly 4-number arrays, but with a special intent. +``pplib`` provides a basic interface for these special arrays:: + + typedef struct { + ppnum lx, ly, rx, ry; + } pprect; + +This type is used only by helper functions - PDF parser is not aware of the rectangle type. +To convert ``pparray`` to ``pprect``:: + + pprect * pparray_to_rect (pparray *array, pprect *rect); // returns rect or NULL + +In example:: + + pprect rect; + if (pparray_to_rect(array, &rect) != NULL) + ; // do something with rect + +To get some image bounding box:: + + pprect * ppdict_get_rect (ppdict *dict, const char *name, pprect *rect); + // eg. ppdict_get_rect(imagedict, "BBox", &rect) + +To get some page box:: + + pprect * ppdict_get_box (ppdict *dict, const char *name, pprect *rect); + // eg. ppdict_get_box(pagedict, "MediaBox", &rect) + +The later not only checks the pagedict, but also goes through parent page nodes. + +Transforms +---------- + +Transformations are given as 6-number arrays, but with a special intent. +``pplib`` provides a basic interface for these special arrays:: + + typedef struct { + ppnum xx, xy, yx, yy, x, y; + } ppmatrix; + +This type is used only by helper functions - PDF parser is not aware of the matrix type. +To convert ``pparray`` to ``ppmatrix``:: + + ppmatrix * pparray_to_matrix (pparray *array, ppmatrix *matrix); + +In example:: + + ppmatrix matrix; + if (pparray_to_matrix(array, &matrix) != NULL) + ; // do something with matrix + +To get the matrix from dict:: + + ppmatrix * ppdict_get_matrix (ppdict *dict, const char *name, ppmatrix *matrix); + // eg. ppdict_get_matrix(imagedict, "Matrix", &matrix) + +Errors handling +--------------- + +``pplib`` is not verbose, but might happen that it needs to log some error message, eg. when parsing +of some PDF boject fails due to invalid offsets. By default, ``pplib`` prints the message to stdout, eg.:: + + invalid 123 0 R object at offset 123123 + +To replace the default logger, you can provide your own:: + + void pplog_callback (pplogger_callback logger, void *alien); + +``pplogger_callback`` is a function:: + + void your_callback (const char *message, void *alien); + +In example, to redirect messages to stderr you may define a function:: + + void your_callback (const char *message, void *alien) + { + fprintf((FILE *)alien, "\nooops: %s\n", message); + } + +Then set the callback somewhere before loading documents:: + + pplog_callback(your_callback, stderr); + +(example 2 uses that). + +To set the default log messages prefix, eg. ``pplib:``, use:: + + int pplog_prefix (const char *prefix) + +Default is empty. The function succeeds if provided prefix is reasonably short (less then 32 bytes). diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-2.x.rst.txt b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-2.x.rst.txt new file mode 100644 index 00000000000..250cd8fcd35 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi-2.x.rst.txt @@ -0,0 +1,937 @@ + +``pplib`` 2.x +============= + +``pplib`` is a library for raw PDF access. It parses PDF documents and provides an interface to access document structures in C. + +C-API +===== + +Types +----- + +``pplib`` defines several C-types to represent PDF types: + +- ``ppbyte`` - char +- ``ppint`` - signed integer (``int64_t``) +- ``ppnum`` - real number (double) +- ``ppname`` - PDF name +- ``ppstring`` - PDF string +- ``pparray`` - PDF array +- ``ppdict`` - PDF dict +- ``ppstream`` - PDF stream +- ``ppref`` - PDF indirect reference +- ``ppobj`` - a container of all above + +Among ``ppint`` and ``ppnum``, we also use ``ppuint`` - unsigned integer (machine word, alias to ``size_t``). + +Other API types: + +- ``ppdoc`` - PDF document +- ``ppxref`` - cross-references table +- ``ppcontext`` - ... later +- ``pprect`` - rectangle +- ``ppmatrix`` - matrix + +Integer and number are as simple types. Names and strings used to be aliases to ``char *`` +in ``pplib 1.x``, now they are structures; all related API functions operate on pointers. +Other types (array, dict, stream, reference, object container, xref, doc) are C-structures, +and you operate it their pointers. So when you declare a simple type variable you say:: + + ppuint u; + ppnum n; + ... + +And when you declare a compound type you operate on pointers:: + + ppobj *obj; + ppname *name; + ppstring *string; + pparray *array; + ppdict *dict; + ppstream *stream; + ppref *ref; + ppdoc *pdf; + +Most of those C-types are defined in library header ``ppapi.h`` (complete types). Some others are incomplete +(eg. you can't say ``sizeof(ppdoc)`` or ``sizeof(ppxref)``). This is to avoid unnecesary dependencies in +the header. The library itself uses ``pplib.h`` header but for auxilary applications including a standalone +``ppapi.h`` header should be enough. + +``pplib`` was designed having **read-only** PDF access in mind. Even if some structure is completelly exposed, +so that you can directly access its members, you should treat them as read-only. I don't make them ``const`` because +then all variable declarations would need to be ``const``, which is annoying, and I'd need some trickery in the library +internals to unconst. Besides, nothing is really const for C type casts. + +Object +------ + +A common container for all elementary PDF object types is ``ppobj`` structure. ``ppobj`` has a type identifier +(integer) and union of values:: + + struct ppobj { + ppobjtp type; + union { + ppint integer; + ppnum number; + ppname *name; + ppstring *string; + pparray *array; + ppdict *dict; + ppstream *stream; + ppref *ref; + void *any; + }; + }; + +Object type is one of constants (enum):: + + PPNONE + PPNULL + PPBOOL + PPINT + PPNUM + PPNAME + PPSTRING + PPARRAY + PPDICT + PPSTREAM + PPREF + +The type determines the structure member you're allowed to access:: + + ppobj *obj; + ... + switch (obj->type) + { + case PPNONE: // shouldn't actually happen, indicates some failure + break; + case PPNULL: // valid PDF null object, no value + break; + case PPBOOL: // do something with obj->integer (ppint), value 0 or 1 + break; + case PPINT: // do something with obj->integer (ppint) + break; + case PPNUM: // do something with obj->number (ppnum) + break; + case PPNAME: // do something with obj->name (ppname *) + break; + case PPSTRING: // do something with obj->string (ppstring *) + break; + case PPARRAY: // do something with obj->array (pparray *) + break; + case PPDICT: // do something with obj->dict (ppdict *) + break; + case PPSTREAM: // do something with obj->stream (ppstream *) + break; + case PPREF: // do something with obj->ref (ppref *) + break; + } + +More often then not you know exactly what type of object value is expected, in which case +you may use one of the following macros:: + + // returns 1 if o->type is PPNULL + int ppobj_get_null(o) \ + + // if o->type is PPBOOL, sets int v to 0 or 1 and returns 1, 0 otherwise + int ppobj_get_bool(o, v) + + // if o->type is PPINT, sets ppint v and returns 1, 0 otherwise + int ppobj_get_int(o, v) + + // if o->type is PPINT and >= 0, sets ppuint v and returns 1, 0 otherwise + int ppobj_get_uint(o, v) + + // if o->type is PPNUM or PPINT, sets ppnum v and returns 1, 0 otherwise + int ppobj_get_num(o, v) + + // if o->type is PPNAME returns the name, NULL otherwise + ppname * ppobj_get_name(o) + + // if o->type is PPSTRING returns the string, NULL otherwise + ppstring * ppobj_get_string(o) + + // if o->type is PPARRAY returns the array, NULL otherwise + pparray * ppobj_get_array(o) + + // if o->type is PPDICT returns the dict, NULL otherwise + ppdict * ppobj_get_dict(o) + + // if o->type is PPSTREAM returns the stream, NULL otherwise + ppstream * ppobj_get_stream(o) + + // if o->type is PPREF returns the reference, NULL otherwise + ppref * ppobj_get_ref(o) + +Note the coercion from integer to real number, but not reverse. In practise, whenever you expect a real number, +you should also handle integer (eg. '1' used instead of '1.0' is pretty common in PDF). + +It is a common case that the object is given as an indirect reference, but what you actually +want is not the reference, but the object referred by it. Here is a helper for it:: + + // if o->type is PPREF, returns what the reference points, otherwise returns o + ppobj * ppobj_rget_obj(o) + +Also every ``ppobj_get_*`` macro has ``ppobj_rget_*`` counterpart that makes a check +for the expected type, but if the object is PPREF, it jumps to the target object. +So for example ``ppobj_rget_dict(obj)`` will return dict if ``obj`` is of type PPDICT +or if it is of type PPREF and ``obj->ref`` hosts an object of type PPDICT. + +Names +----- + +PDF names are represented as ``ppname`` pointer (``ppname`` used to be an alias to ``char *``, now it is a structure). +To access the name data:: + + ppbyte * ppname_data(name) // name->data, bytes array + +For convenient use in C, names are ``'\0'`` terminated. But to get the length of name better always use +``ppname_size()`` macro. ``ppname`` object knows its size, don't use ``strlen()``:: + + size_t ppname_size(ppname name); // name->size, the length of name in bytes + +In current implementation names are not hashed anyhow, so name-to-name comparison is not smarter than ``memcmp()``. +Use macros:: + + int ppname_is(ppname name, "literal"); // to compare ppname with C-literal string + int ppname_eq(ppname name, ppname other); // to compare ppname with a different name + +If you use ``pplib`` to parse contents streams, you may need to distinguish names from operators +(more precisely executable names). Names in PDF are preceeded by '/', executable names aren't. In both +cases PDF parser will produce ``ppname`` but the result can be distingushed with:: + + int ppname_exec(ppname name); // macro, returns non-zero if the name is executable + +Names are kept in their raw form, with possible PDF specific escapes (in text below we call it **encoded** form). +Leading '/' is omitted. One may need a decoded name, with no PDF escapes. +A pair of functions provides a simple interface to switch between those two forms:: + + // these helpers rely on name->alterego member + ppname * ppname_decoded (ppname *name); // returns decoded (unescaped) form of the name + ppname * ppname_encoded (ppname *name); // returns encoded (escaped) form of the name + ppbyte * ppname_decoded_data (ppname *name); + ppbyte * ppname_encoded_data (ppname *name); + +In pretty most cases a PDF name contains only letters (no special characters, no escapes), so decoded and encoded forms are identical. +In that case both functions simply return the argument. It is ok to call ``ppname_decoded()`` on already decoded form +and ``ppname_encoded()`` on already encoded form. Both forms are produced by PDF objects parser, so accessing ``ppname`` alter ego +in whatever direction needs no extra decoding or allocation costs (the cost is paid by parser). + +String +------ + +PDF strings have the same internal construction as names, so most of names description above applies to strings as well. +``ppstring`` is a structure (used to be an alias to ``char *``). ``string->data`` is ``\0``-terminated c-array of ``ppbytes``. +To get the data:: + + ppbyte * ppstring_data(ppstring *string); // string->data, macro + +To get the size of the string:: + + size_t ppstring_size(ppstring *string); // macro, returns the length of the string in bytes + +Strings are provided in their raw form, preserving PDF specific escapes, but with no +``()`` or ``<>`` delims. To distinguish plain strings from hex strings:: + + int ppstring_hex(ppstring string); // macro, returns non zero if hex string + +Or if you prefer:: + + switch (ppstring_type(string)) + { + case PPSTRING_PLAIN: // literal string, surrounded by ``(`` and ``)`` in PDF + break; + case PPSTRING_BASE16: // hex string, surrounded by ``<`` and ``>`` in PDF + break; + case PPSTRING_BASE85: // base85 string surrounded by ``<~`` and ``~>`` in PDF + break; + } + +The last is actually Postscript specific, not used in PDF, but I think it might appear in contents streams... +No matter how the string is given in PDF (plain or hex), here are two functions to +switch between encoded and decoded strings forms:: + + ppstring * ppstring_decoded (ppstring *string); // returns decoded string possibly with PDF escapes + ppstring * ppstring_encoded (ppstring *string); // returns encoded string with no PDF escapes + ppbyte * ppstring_decoded_data (ppstring *string); + ppbyte * ppstring_encoded_data (ppstring *string); + +For hex strings, encoded form contains hex digits, while decoded form contains arbitrary bytes (the result of hex decoding). +Plain strings usually contains printable ASCII characters, but they might contain any binary data. +As with names, objects parser produces both forms. The raw form with PDF escapes (or raw hex form) the main one. +Eg. when you access ``obj->string`` you always get the encoded form. At any moment you can switch to its alter ego. + +No matter if the string is plain or hex, if its first two bytes (decoded) are UTF16 BOM, the string is unicode. +``ppstring`` object *knows* it is unicode or not:: + + switch (ppstring_utf(string)) + { + case PPSTRING_UTF16LE: // unicode string, utf16le + break; + case PPSTRING_UTF16BE: // unicode string, utf16be + break; + default: // no unicode + } + +Or simply:: + + if (ppstring_utf(string) != 0) { + // handle unicode string + } + +If the string is unicode, BOM remains the part of the string -- ``pplib`` parser does not strip it. +Unicode or not, encoded or decoded, strings are always C-arrays of bytes and ``ppstring_size()`` +always returns the size in bytes. + +Array +----- + +PDF arrays are represented as ``pparray`` type, which is C-array of ``ppobj`` structures. +To get the size:: + + size_t pparray_size(pparray *array) // macro, returns the number of array items + +To get ``ppobj *`` at a given index:: + + ppobj * pparray_at(array, index) // macro, returns ppobj * (no index check) + ppobj * pparray_get(array, index) // macro, returns ppobj * or NULL (with index check) + ppobj * pparray_get_obj (pparray *array, size_t index); // function equiv to pparray_get() + +Iterating over array elements:: + + pparray *array; + size_t index, size; + ppobj *obj; + for (size = pparray_size(array), pparray_first(array, index, obj); index < size; pparray_next(index, obj)) + { + // do something with index and obj + } + +There is no magic first/next macros, just iteration over pointers. One could also use something like:: + + for (index = 0, size = array->size; index < size; ++index) + { + obj = pparray_at(array, index); + // do something with index and obj + } + +When getting values from array and expecting a result of known type, use one of the following:: + + int pparray_get_bool (pparray *array, size_t index, int *v); // get boolean value + int pparray_get_int (pparray *array, size_t index, ppint *v); // get ppint value + int pparray_get_uint (pparray *array, size_t index, ppuint *v); // get ppuint value + int pparray_get_num (pparray *array, size_t index, ppnum *v); // get ppnum value + ppname * pparray_get_name (pparray *array, size_t index); // get ppname * value + ppstring * pparray_get_string (pparray *array, size_t index); // get ppstring * value + pparray * pparray_get_array (pparray *array, size_t index); // get pparray * value + ppdict * pparray_get_dict (pparray *array, size_t index); // get ppdict * value + ppref * pparray_get_ref (pparray *array, size_t index); // get ppref * value + +As with ``ppobj_get_*`` suite, numeric types getters set the value of a given type and returns 1, if the type matches. +Otherwise sets nothing and returns 0. Other getters return the value if the type matches, or NULL. + +Every function from ``pparray_get_*`` suite have its ``pparray_rget_*`` counterpart +that dereferences indirect objects (as explained for ``ppobj_rget_*`` getters). Note that +there is no ``pparray_get_stream()`` function, as streams in PDF are always indirect +(may only reside in ``ref->object.stream``). To get the stream from array use:: + + ppstream * pparray_rget_stream (pparray *array, size_t index); + +Dict +---- + +PDF dicts are represented as ``ppdict`` structure, which is C-array of ``ppobj`` with parallel +C-array of ``ppname`` pointers. To get the size of a dict:: + + size_t ppdict_size(ppdict *dict) // macro, returns the number of key-val pairs + +To get the value at a given index (integer):: + + ppobj * ppdict_at(ppdict *dict, index) // macro, no index bounds check + +To get the name (key) at a given index:: + + ppname * ppdict_key(ppdict *dict, index) // macro, no index bounds check + +To iterate over dict key-val pairs:: + + ppdict *dict; + ppname **pkey; + ppobj *obj; + + for (ppdict_first(dict, pkey, obj); *pkey != NULL; ppdict_next(pkey, obj)) + { + // do something with *pkey and obj + } + +There is no magic in first/next macros, just iteration through keys and values lists pointers. +For convenient iteration, a list of keys is terminated with NULL, so in the code above ``*pkey != NULL`` +is used as the loop condition. One may also iterate via indices:: + + ppdict *dict; + size_t index, size; + ppname *key; + ppobj *obj; + for (index = 0, size = ppdict_size(dict); index < size; ++index) + { + key = ppdict_key(dict, index); + obj = ppdict_at(dict, index); + // do something with key and obj + } + +To get the object associated with a given name, use one of the following:: + + ppobj * ppdict_get_obj (ppdict *dict, const char *name); + int ppdict_get_bool (ppdict *dict, const char *name, int *v); + int ppdict_get_int (ppdict *dict, const char *name, ppint *v); + int ppdict_get_uint (ppdict *dict, const char *name, ppuint *v); + int ppdict_get_num (ppdict *dict, const char *name, ppnum *v); + ppname ppdict_get_name (ppdict *dict, const char *name); + ppstring ppdict_get_string (ppdict *dict, const char *name); + pparray * ppdict_get_array (ppdict *dict, const char *name); + ppdict * ppdict_get_dict (ppdict *dict, const char *name); + ppref * ppdict_get_ref (ppdict *dict, const char *name); + +Note that all getters accepts ``const char *`` as key, so it is ok to say:: + + ppdict_rget_dict(dict, "Resources"); + +(the most common use I guess). But to use ``ppname`` object as a key, one have to +use data member:: + + ppdic_rget_dict(dict, name->data); // ppname *name + +Every ``ppdict_get_*`` getter has ``ppdict_rget_*`` counterpart that dereferences +indirect objects if necessary. Note that there is no ``ppdict_get_stream()`` function, +but there is:: + + ppstream * ppdict_rget_stream (ppdict *dict, const char *name); + +So far dicts comes with no names mapping, so by-name dict accessors perform a linear search +through the keys list. PDF dicts are usually small. + +Stream +------ + +PDF streams are represented as ``ppstream`` objects. To get the stream dict:: + + ppdict * ppstream_dict(ppstream *stream) // macro + +To read the stream data:: + + uint8_t * ppstream_first (ppstream *stream, size_t *size, int decode); + uint8_t * ppstream_next (ppstream *stream, size_t *size); + void ppstream_done (ppstream *stream); + +Both ``first` and ``next`` functions return a chunk of stream data and sets the ``size`` of the chunk. +``decode`` parameter tell the reader to decompress the stream (1) or return raw (0). A call to ``ppstream_next()`` +must be preceeded by ``ppstream_first()``. Once you're done with the stream, you have to call ``ppstream_done()``, +no matter if the stream has been read to the end or not. The stream data iterator in use:: + + uint8_t *data; + size_t size; + ppstream *stream; + int decode = 1; // 1 - get decompressed, 0 - get raw + + for (data = ppstream_first(stream, &size, decode); data != NULL; data = ppstream_next(stream, &size)) + { + // do something with data and its size + } + ppstream_done(stream); + +Every subsequent iterator call invalidates the previous reader output, so you have to utilize the returned chunk +of data just after you ot that. So the following is wrong:: + + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_next(stream, &size); + data3 = ppstream_next(stream, &size); + some_output(data1, size); + some_output(data2, size); + +The reader calls usually return the same pointer to internal buffer, just filled with a different data. +``pplib`` allocates reasonably large buffer and fills that buffer on subsequent calls to the reader. + +If the source stream has no compression, using both ``decode == 1`` and ``decode == 0`` should give the same result. +You can check if the stream is actually compressed with:: + + ppstream_compressed(stream) // macro, returns non zero if /Filter is present + +It might be necessary to load the entire stream data at once:: + + uint8_t * ppstream_all (ppstream *stream, size_t *size, int decode); + +If the initial buffer size is insufficient, it grows until the entire stream data is loaded. You must call +``ppstream_done(stream)`` after using returned data. + +``ppstream_done()`` doesn't invalidate the stream object, it just closes its internal reader. +The stream itself remains a valid object (eg. one can read it again if necessary), +but the reader buffer is released. It is actually not freed but kept for future the reuse with that on some other stream, +but you still need to mark it ready for reuse to avoid allocating a separate buffer for every stream you're going to read. + +Stream data readers will return ``NULL`` if you haven't close the previous reader process with ``ppstream_done()``. All below is wrong:: + + data1 = ppstream_all(stream, &size, 1); + data2 = ppstream_all(stream, &size, 1); // data2 == NULL + // or + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_first(stream, &size, 1); // data2 == NULL + // or + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_all(stream, &size, 1); // data2 == NULL + +To avoid unnecessary dependencies, ``pplib`` does not support image filters (``/DCT``, ``/JPX``, ``/JBIG``, ``/CCITT``). +But it is ok to read the stream with ``decode`` set to 1 on such streams. ``pplib`` assumes that the image is the +final/target stream form and just returns it as-is. Eg. in the case of JPEG (``/DCT`` filtered) image both calls should +give the same results:: + + ppstream_all(jpegstream, &jpegsize, 0); // don't decode, return what's there + ppstream_all(jpegstream, &jpegsize, 1); // decode but found image filter, effectively the same + +A bit more about streams memory. As mentioned, ``pplib`` allocates buffers for stream readers. After ``ppstream_done()``, +the stream no longer *owns* the buffer space. But the buffer may remain allocated, to be reused with future readers. +``pplib`` keeps a pool of several buffers. This means, that when you use stream readers, ``pplib`` eats +some memory (1MB or so) that is not freed, even if no streams are used. And even if you free all objects. +If you suffer from this, you can optionally use a pair of functions:: + + void ppstream_init_buffers (void); + void ppstream_free_buffers (void); + +The first initializes buffers pool, unless done so far. Currently ``pplib`` cares of it before opening every stream reader, +so it is not obligatory. The second frees a pool of buffers. The intended use is to call ``ppstream_init_buffers()`` once +as kind of library initializer and to call ``ppstream_free_buffers()`` once, as the library finalizer. + +Filters +------- + +``ppstream`` knows its filter(s) and keps it as ``stream->filter``:: + + // ppstream *stream; + ppstream_filter *info = &stream->filter; + +``ppstream_filter`` is the following structure:: + + typedef struct { + ppstreamtp *filters; // c-array of filter identifiers (enum integers) + ppdict **params; // c-array of ppdict pointers + size_t count; // number of filters, length of the arrays (typically 1) + } ppstream_filter; + +If ``count > 0`` then ``filters`` member is not NULL. Filters array keeps integer constants:: + + PPSTREAM_BASE16 /* /ASCIIHexDecode */ + PPSTREAM_BASE85 /* /ASCII85Decode */ + PPSTREAM_RUNLENGTH /* /RunLengthDecode */ + PPSTREAM_FLATE /* /FlateDecode */ + PPSTREAM_LZW /* /LZWDecode */ + PPSTREAM_CCITT /* /CCITTFaxDecode */ + PPSTREAM_DCT /* /DCTDecode */ + PPSTREAM_JBIG2 /* /JBIG2Decode */ + PPSTREAM_JPX /* /JPXDecode */ + PPSTREAM_CRYPT /* /Crypt */ + +Params array keeps corresponding filter parameters (``/DecodeParms``) if present. ``params`` member is not NULL +if ``count > 0`` and the stream dict has ``/DecodeParms`` entry. Even if ``params`` is there, +for every N-th filter, ``params[N]`` may be NULL (corresponding to PDF ``null``). + +``stream->filter`` keeps the source stream filter information, which may not correspond to the result of stream readers +(``ppstream_first()``, ``ppstream_next()``, ``ppstream_all()``). The get the filters info relevant to the result from readers:: + + void ppstream_filter_info (ppstream *stream, ppstream_filter *info, int decode); + +The function fills ``ppstream_filter`` structure according to the expected result from stream readers (example 3 shows +how to use it to reconstruct ``/Filter`` and ``/DecodeParms`` when copying the stream to some other PDF). + +To convert filter identifier (``ppstreamtp``) to a corresponding PDF filter name:: + + const char * ppstream_filter_name[]; + +To covert ``ppname`` to filter identifier:: + + int ppstream_filter_type (ppname filtername, ppstreamtp *filtertype); + // returns 1 and sets filtertype if filtername is the proper filter name + +Additional information about the stream can be fetched from macros:: + + ppstream_compressed(stream) /* stream->flags & (PPSTREAM_FILTER|PPSTREAM_IMAGE) */ + ppstream_filtered(stream) /* stream->flags & PPSTREAM_FILTER */ + ppstream_image(stream) /* stream->flags * PPSTREAM_IMAGE */ + +``stream->flags`` is a binary sum of the following:: + + PPSTREAM_FILTER /* set iff the stream filters list has one of: BASE16, BASE85, RUNLENGTH, FLATE, LZW */ + PPSTREAM_IMAGE /* set iff the stream filters list has one of: CCITT, DCT, JBIG2, JPX */ + PPSTREAM_ENCRYPTED /* set iff the stream is encrypted */ + PPSTREAM_ENCRYPTED_OWN /* set iff the stream has own CRYPT filter */ + +Note that ``PPSTREAM_COMPRESSED`` is not there any longer, use ``ppstream_compressed()`` instead. +And there is some more, see ``ppapi.h``. + +Ref +--- + +Indirect objects are represented as ``ppref`` structure. To get the object that the +reference refers to:: + + ppobj * ppref_obj(ppref *ref) // macro + +``ppref`` structure also keeps the reference number and version, a pointer to cross reference table it belongs +to and others, but I guess you won't need anything but the referenced object. ``pplib`` parser resolves references +on-fly. So if there is a dict with indirect objects:: + + << + /Type /Page + /Resources 123 0 R + ... + >> + +the parser will produce ``ppdict`` with ``Resources`` key pointing the proper ``ppref *`` value. +If you need more, access ``ppref`` members:: + + struct ppref { + ppobj object; // target object + ppuint number, version; // identifiers + size_t offset; // file offset (useless for you, may be zero for compressed objects) + ppuint length; // the length of the original object data + ppxref *xref; // cross reference table it belongs to + }; + + +XRef +---- + +Cross reference table is exposed as ``ppxref`` (incomplete type, you can only oprate on its pointer). +To get top document xref:: + + ppxref * ppdoc_xref (ppdoc *pdf); + +To get previous (older) xref:: + + ppxref * ppxref_prev (ppxref *xref); + +To find an object of a given refnumber:: + + ppref * ppxref_find (ppxref *xref, ppuint refnumber); + +[Note: since pplib v0.98 in case of documents with incremental update, ``ppxref_find()`` returns +the newest available version of a given object rather than the object in a given body.] + +PDF +--- + +PDF document is represented as ``ppdoc`` structure (incomplete type, you can only operate on its pointer). +To load a document from file:: + + ppdoc * ppdoc_load (const char *filename); + +To load a document from file handle:: + + ppdoc * ppdoc_filehandle (FILE *file, int closefile); // closefile 1 to fclose() on end + +To load a document from memory data:: + + ppdoc * ppdoc_mem (const void *data, size_t size); + +The data is assumed to be a buffer allocated with ``malloc`` - it is freed when destroying ``ppdoc``. + +Both loaders returns ``NULL`` on failure. + +To free ``ppdoc`` and all objects it refers to:: + + void ppdoc_free (ppdoc *pdf); + +So far we haven't mention about any explicit object reclaimers. There are no dedicated ``free`` functions +for other objects. You don't allocate or free objects yourself. ``ppdoc`` object is an owner of all +beings it refers to. It also means that every object described so far is alive as long as the containing +``ppdoc`` is alive. + +To access main PDF dicts:: + + ppdict * ppdoc_trailer(ppdoc *pdf); // returns top xref trailer dict + ppdict * ppdoc_catalog(ppdoc *pdf); // returns catalog referred from the trailer + ppdict * ppdoc_info(ppdoc *pdf); // returns info dict referred from the trailer + +To get the PDF version:: + + const char * ppdoc_version_string (ppdoc *pdf); // version string + int ppdoc_version_number (ppdoc *pdf, int *minor); // minor and major numbers + +To get the file size of the source PDF document:: + + size_t ppdoc_file_size (ppdoc *pdf); + +To get the number of objects in all xrefs:: + + ppuint ppdoc_objects (ppdoc *pdf); + +To get the approx usage of memory:: + + size_t ppdoc_memory (ppdoc *pdf, size_t *waste); + +Encryption +---------- + +``pplib`` handles encrypted (password protected) documents. If a document is encrypted, most of strings and streams are ciphered. +In that form they are unreadable and rather useless, you can't even rewrite such strings/streams as-is to a different PDF output. +It is a common practise to *protect* documents with an empty password. Such documents remain readable in Acrobat (just opens them without prompting +for a password), but some features (eg. printing) may restricted by the application. + +When ``pplib`` detects encryption, it follows Acrobat approach and first tries an empty password. If it succeeds, ``pplib`` proceeeds normally, providing +an access to decrypted strings and streams, as if they weren't ciphered. If the document is protected with non-empty password, ``pplib`` gives +a way to provide a password and proceed. Until you provide a password, ``ppdoc`` object returned by ``ppdoc_load()`` function has all object wntries +set to ``null``. + +After loading a document you should check encryption status with:: + + ppcrypt_status ppdoc_crypt_status (ppdoc *pdf); + +``ppcrypt_status`` (integer) may have the following values: + + ``PPCRYPT_NONE`` - no encryption, go ahead + ``PPCRYPT_DONE`` - encryption present but password succeeded, go ahead + ``PPCRYPT_PASS`` - encryption present, need non-empty password + ``PPCRYPT_FAIL`` - invalid or unsupported encryption (eg. undocumented in pdf spec) + +If a password is needed, you can provide one with:: + + ppcrypt_status ppdoc_crypt_pass (ppdoc *pdf, const void *userpass, size_t userpasslength, + const void *ownerpass, size_t ownerpasslength); + +Well, yes, there are actually two passwords in encrypted documents. Relation between them is obscure to me, but enough +to know that having one of them is enough to decrypt the document. If you know the password, you probably mean +``userpass``, in which case you should put ``NULL`` as ``ownerpass``. The function returns ``PPCRYPT_DONE`` if the password +succeeds and the previous status otherwise. Your custom loader function may look like that:: + + ppdoc *pdf; + pdf = ppdoc_load("file.pdf"); + if (pdf == NULL) + return NULL; + switch (ppdoc_crypt_status(pdf)) + { + case PPCRYPT_NONE: + case PPCRYPT_DONE: + return pdf; + case PPCRYPT_PASS: + if (ppdoc_crypt_pass(pdf, "dummy", 5, NULL, 0) == PPCRYPT_DONE || + ppdoc_crypt_pass(pdf, NULL, 0, "dummy", 5) == PPCRYPT_DONE) + return pdf; + printf("sorry, password needed\n"); + ppdoc_free(pdf); + return NULL; + case PPCRYPT_FAIL: + printf("sorry, encryption failed\n"); + ppdoc_free(pdf); + return NULL; + } + +[If you get ``PPCRYPT_FAIL`` it might mean *I failed*, so treat as a bug.] + +If you'd like to know what permissions are given/restricted to encrypted document:: + + ppint ppdoc_permissions (ppdoc *pdf); + +Returned value can be queried with the following binary flags (you can verify with Acrobat *File -> Properties -> Security* tab):: + + PPDOC_ALLOW_PRINT // printing + PPDOC_ALLOW_MODIFY // filling form fields, signing, creating template pages + PPDOC_ALLOW_COPY // copying, copying for accessibility + PPDOC_ALLOW_ANNOTS // filling form fields, copying, signing + PPDOC_ALLOW_EXTRACT // contents copying for accessibility + PPDOC_ALLOW_ASSEMBLY // (no effect) + PPDOC_ALLOW_PRINT_HIRES // (no effect) + +``pplib`` does absolutelly nothing with permissions, it cares only to decrypt the document. As mentioned, encryption applies to strings +and streams. ``pplib`` decrypt strings when parsing document objects, so the result you get is *normal* (not ciphered). +Streams are decrypted whenever you access them. Even if you ask for a raw stream data, you'll get a raw (compressed) stream, but decrypted. +So except the check to ``ppdoc_crypt_status()``, you shouldn't bother about encryption. + +In encrypted documents most of streams are encrypted. To check if a given stream is encrypted:: + + ppstream_encrypted(stream) // macro, returns non-zero if encrypted + +Encryption is independent from compression, don't confuse with ``ppstream_compressed()`` + +Pages +----- + +Several helpers to deal with pages. To get the number of pages:: + + ppuint ppdoc_page_count (ppdoc *pdf); + +To access the root pages tree node:: + + ppref * ppdoc_pages(ppdoc *pdf); + +To get the page reference at a given index:: + + ppref * ppdoc_page (ppdoc *pdf, ppuint index); + +``index`` is a page number. First page has number 1. For index out of bounds ``ppdoc_page()`` returns NULL. +Iterating over pages using index from 1 to ``ppdoc_page_count()`` and calling ``ppdoc_page()`` on each iteration +would be suboptimal. Here is a dedicted iterator for this:: + + ppref * ppdoc_first_page (ppdoc *pdf); + ppref * ppdoc_next_page (ppdoc *pdf); + +The iterator in use:: + + ppdoc *pdf; + ppref *ref; + ppdict *dict; + int pageno; + + pdf = ppdoc_load("file.pdf"); + for (ref = ppdoc_first_page(pdf), pageno = 1; ref != NULL; ref = ppdoc_next_page(pdf), ++pageno) + { + dict = ppref_obj(obj)->dict; // take for granted it is a dict + // do something with the page dict + } + +Functions related to pages return ``ppref *`` ensured to contain dict object, so you don't need sanity +type checks here. + +Contents +-------- + +PDF page contents can be given as a stream or array of streams. Here is a convenience iterator over page +contents streams:: + + ppstream * ppcontents_first (ppdict *dict); + ppstream * ppcontents_next (ppdict *dict, ppstream *stream); + +A complete example of contents stream parser use is given below (example 2). +But before we get there, we need to introduce ``ppcontext`` object. Conceptually, +``ppcontext`` is an owner (memory handler) of objects created on demand (beyond the ``ppdoc``). +So far used only with contents stream parser, which might produce quite some data that we want +to release just after used. To create a new context:: + + pcontext * ppcontext_new (void); + +It initializes a new context and its internal memory heap, taking about 64kB on start. After that, +the context is ready to produce objects (contents parsing functions below). Once objects produced +from a given context are no longer needed:: + + void ppcontext_done (ppcontext *context); + +It restores the context to its initial state, as after ``ppcontext_new()``. It means that the context +is ready to produce another bunch of beings (in the example below, all objects from the next page contents). +Once the context is not needed anymore:: + + void ppcontext_free (ppcontext *context); + +Now, contents stream parser functions take the context as an argument. Iterator form of contents stream parser +that allows to process the contents operator by operator:: + + ppobj * ppcontents_first_op (ppcontext *context, ppstream *stream, size_t *psize, ppname *pname); + ppobj * ppcontents_next_op (ppcontext *context, ppstream *stream, size_t *psize, ppname *pname); + +Returned ``ppobj *`` is a pointer to operands list. ``*psize`` is the number of operands on stack. +The operator itself is stored as ``*pname``. + +To parse the entire contents stream at once with no stop at every operator:: + + ppobj * ppcontents_parse (ppcontext *context, ppstream *stream, size_t *psize); + +Returns probably quite long list of all parsed objects (operands and operatos) in one piece. +The number of objects is stored to ``*psize``. + +[Contents may contain so called inline images, that breaks a simple scheme of operands / operator syntax:: + + BI ID EI + +Contents parser treats this genuine triplet as a single piece, producing two operands (dict and string) +followed by ``EI`` operator name.] + +Boxes +----- + +Boxes (rectangles) in PDF are roughly 4-number arrays, but with a special intent. +``pplib`` provides a basic interface for these special arrays:: + + typedef struct { + ppnum lx, ly, rx, ry; + } pprect; + +This type is used only by helper functions - PDF parser is not aware of the rectangle type. +To convert ``pparray`` to ``pprect``:: + + pprect * pparray_to_rect (pparray *array, pprect *rect); // returns rect or NULL + +In example:: + + pprect rect; + if (pparray_to_rect(array, &rect) != NULL) + ; // do something with rect + +To get some image bounding box:: + + pprect * ppdict_get_rect (ppdict *dict, const char *name, pprect *rect); + // eg. ppdict_get_rect(imagedict, "BBox", &rect) + +To get some page box:: + + pprect * ppdict_get_box (ppdict *dict, const char *name, pprect *rect); + // eg. ppdict_get_box(pagedict, "MediaBox", &rect) + +The later not only checks the pagedict, but also goes through parent page nodes. + +Transforms +---------- + +Transformations are given as 6-number arrays, but with a special intent. +``pplib`` provides a basic interface for these special arrays:: + + typedef struct { + ppnum xx, xy, yx, yy, x, y; + } ppmatrix; + +This type is used only by helper functions - PDF parser is not aware of the matrix type. +To convert ``pparray`` to ``ppmatrix``:: + + ppmatrix * pparray_to_matrix (pparray *array, ppmatrix *matrix); + +In example:: + + ppmatrix matrix; + if (pparray_to_matrix(array, &matrix) != NULL) + ; // do something with matrix + +To get the matrix from dict:: + + ppmatrix * ppdict_get_matrix (ppdict *dict, const char *name, ppmatrix *matrix); + // eg. ppdict_get_matrix(imagedict, "Matrix", &matrix) + +Errors handling +--------------- + +``pplib`` is not verbose, but might happen that it needs to log some error message, eg. when parsing +of some PDF boject fails due to invalid offsets. By default, ``pplib`` prints the message to stdout, eg.:: + + invalid 123 0 R object at offset 123123 + +To replace the default logger, you can provide your own:: + + void pplog_callback (pplogger_callback logger, void *alien); + +``pplogger_callback`` is a function:: + + void your_callback (const char *message, void *alien); + +In example, to redirect messages to stderr you may define a function:: + + void your_callback (const char *message, void *alien) + { + fprintf((FILE *)alien, "\nooops: %s\n", message); + } + +Then set the callback somewhere before loading documents:: + + pplog_callback(your_callback, stderr); + +(example 2 uses that). + +To set the default log messages prefix, eg. ``pplib:``, use:: + + int pplog_prefix (const char *prefix) + +Default is empty. The function succeeds if provided prefix is reasonably short (less then 32 bytes). diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi.rst.txt b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi.rst.txt new file mode 100644 index 00000000000..5d1d2883e57 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppapi.rst.txt @@ -0,0 +1,937 @@ + +``pplib`` +========= + +``pplib`` is a library for raw PDF access. It parses PDF documents and provides an interface to access document structures in C. + +C-API +===== + +Types +----- + +``pplib`` defines several C-types to represent PDF types: + +- ``ppint`` - signed integer (``int64_t``) +- ``ppnum`` - real number (double) +- ``ppname`` - PDF name +- ``ppstring`` - PDF string +- ``pparray`` - PDF array +- ``ppdict`` - PDF dict +- ``ppstream`` - PDF stream +- ``ppref`` - PDF indirect reference +- ``ppobj`` - a container of all above + +Among ``ppint`` and ``ppnum``, we also use ``ppuint`` - unsigned integer (machine word, alias to ``size_t``). + +Other API types: + +- ``ppdoc`` - PDF document +- ``ppxref`` - cross-references table +- ``ppcontext`` - ... later +- ``pprect`` - rectangle +- ``ppmatrix`` - matrix + +Integer, number, name and string are treated as simple types. +Names and strings are actually C-structures, but exposed to API as typedefs to ``const char *``. +Other types (array, dict, stream, reference, object container, xref, PDF) are C-structures, +and you operate it their pointers. So when you declare a simple type variable you say:: + + ppuint u; + ppnum n; + ppname name; + ppstring string; + ... + +And when you declare a compound type you operate on pointers:: + + ppobj *obj; + pparray *array; + ppdict *dict; + ppstream *stream; + ppref *ref; + ppdoc *pdf; + +Some of those C-types are defined in library header ``ppapi.h`` (complete types). Some others are incomplete +(eg. you can't say ``sizeof(ppdoc)`` or ``sizeof(ppxref)``). This is to avoid unnecesary dependencies in +the header. [At some points it's not clear to me what to hide and what to expose, will see.] The library itself +uses ``pplib.h`` but for auxilary applications including a standalone ``ppapi.h`` header should be enough. + +``pplib`` was designed having **read-only** PDF access in mind. Even if some structure is completelly exposed, +so that you can directly access its members, you should treat them as read-only. I don't make them ``const`` because +then all variable declarations would need to be ``const``, which is annoying, and I'd need some trickery in the library +internals to unconst. Besides, nothing is really const for C type casts. + +Object +------ + +A common container for all elementary PDF object types is ``ppobj`` structure. ``ppobj`` has a type identifier +(integer) and union of values:: + + struct ppobj { + ppobjtp type; + union { + ppint integer; + ppnum number; + ppname name; + ppstring string; + pparray *array; + ppdict *dict; + ppstream *stream; + ppref *ref; + void *any; + }; + }; + +Object type is one of constants (enum):: + + PPNONE + PPNULL + PPBOOL + PPINT + PPNUM + PPNAME + PPSTRING + PPARRAY + PPDICT + PPSTREAM + PPREF + +The type determines the structure member you're allowed to access:: + + ppobj *obj; + ... + switch (obj->type) + { + case PPNONE: // shouldn't actually happen, indicates some failure + break; + case PPNULL: // valid PDF null object, no value + break; + case PPBOOL: // do something with obj->integer (ppint), value 0 or 1 + break; + case PPINT: // do something with obj->integer (ppint) + break; + case PPNUM: // do something with obj->number (ppnum) + break; + case PPNAME: // do something with obj->name (ppname) + break; + case PPSTRING: // do something with obj->string (ppstring) + break; + case PPARRAY: // do something with obj->array (pparray *) + break; + case PPDICT: // do something with obj->dict (ppdict *) + break; + case PPSTREAM: // do something with obj->stream (ppstream *) + break; + case PPREF: // do something with obj->ref (ppref *) + break; + } + +More often then not you know exactly what type of object value is expected, in which case +you may use one of the following macros:: + + // returns 1 if o->type is PPNULL + int ppobj_get_null(o) \ + + // if o->type is PPBOOL, sets int v to 0 or 1 and returns 1, 0 otherwise + int ppobj_get_bool(o, v) + + // if o->type is PPINT, sets ppint v and returns 1, 0 otherwise + int ppobj_get_int(o, v) + + // if o->type is PPINT and >= 0, sets ppuint v and returns 1, 0 otherwise + int ppobj_get_uint(o, v) + + // if o->type is PPNUM or PPINT, sets ppnum v and returns 1, 0 otherwise + int ppobj_get_num(o, v) + + // if o->type is PPNAME returns the name, NULL otherwise + ppname ppobj_get_name(o) + + // if o->type is PPSTRING returns the string, NULL otherwise + ppstring ppobj_get_string(o) + + // if o->type is PPARRAY returns the array, NULL otherwise + pparray * ppobj_get_array(o) + + // if o->type is PPDICT returns the dict, NULL otherwise + ppdict * ppobj_get_dict(o) + + // if o->type is PPSTREAM returns the stream, NULL otherwise + ppstream * ppobj_get_stream(o) + + // if o->type is PPREF returns the reference, NULL otherwise + ppref * ppobj_get_ref(o) + +Note the coercion from integer to real number, but not reverse. In practise, whenever you expect a real number, +you should also handle integer (eg. '1' used instead of '1.0'). + +It is a common case that the object is given as an indirect reference, but what you actually +want is not the reference, but the object referred by it. Here is a helper for it:: + + // if o->type is PPREF, returns what the reference points, otherwise returns o + ppobj * ppobj_rget_obj(o) + +Also every ``ppobj_get_*`` macro has ``ppobj_rget_*`` counterpart that makes a check +for the expected type, but if the object is PPREF, it jumps to the target object. +So for example ``ppobj_rget_dict(obj)`` will return dict if ``obj`` is of type PPDICT +or if it is of type PPREF and ``obj->ref`` hosts an object of type PPDICT. + +Names +----- + +PDF names are represented as ``ppname``. +I find it convenient to have ``ppname`` type pretending ``const char *``. This allows to use ``ppname`` +in all C-style string functions like ``printf("%s", name)``. + +Be aware, however, that ``ppname`` is actually a C-structure. It is perfectly ok to cast ``ppname`` to ``const char *``:: + + ppname name; + ... + (const char *)name; + +But reverse is forbidden:: + + const char *cstr = "cstring"; + ... + (ppname)cstr; // expect segmentation fault soon + +For convenient use in C, names are ``'\0'`` terminated. But to get the length of name better always use +``ppname_size()`` macro. ``ppname`` object knows its size, don't use ``strlen()``:: + + size_t ppname_size(ppname name); // macro, returns length of name in bytes + +In current implementation names are not hashed anyhow, so name-to-name comparison is not smarter than ``memcmp()``. +Use macros:: + + int ppname_is(ppname name, "literal"); // to compare ppname with C-literal string + int ppname_eq(ppname name, ppname other); // to compare ppname with a different name + +If you'll use ``pplib`` to parse contents streams, you may need to distinguish names from operators +(more precisely executable names). Names in PDF are preceeded by '/', executable names aren't. In both +cases PDF parser will produce ``ppname`` but can be distingushed with:: + + int ppname_exec(ppname name); // returns non-zero if name is executable + +Names are kept in their raw form, with possible PDF specific escapes (in text below we call it **encoded** form). +Leading '/' is omitted, though. One may need a decoded name, with no PDF escapes. +A pair of functions provides a simple interface to switch between those two forms:: + + ppname ppname_decoded (ppname name); // returns decoded (unescaped) form of the name + ppname ppname_encoded (ppname name); // returns encoded (escaped) form of the name + +In pretty most cases PDF names contains only letters (no special characters, no escapes), so decoded and encoded forms are identical. +In that case both functions simply return the argument. It is ok to call ``ppname_decoded()`` on already decoded form +and ``ppname_encoded()`` on already encoded form. Both forms are produced by PDF objects parser, so accessing ``ppname`` alter ego +in whatever direction needs no extra decoding or allocation costs. + +String +------ + +PDF strings have the same internal construction as names, so most of names description above applies to strings as well. +``ppstring`` is a typedef of ``const char *``, roughly ``'\0'`` terminiated C-string. To get the size of the string:: + + size_t ppstring_size(ppstring string); // macro, returns the length of the string in bytes + +Strings are provided in their raw form, preserving PDF specific escapes, but with no +``()`` or ``<>`` delims. To distinguish plain strings from hex strings:: + + int ppstring_hex(ppstring string); // macro, returns non zero if hex string + +Or if you prefer:: + + switch (ppstring_type(string)) + { + case PPSTRING_PLAIN: // literal string, surrounded by ``(`` and ``)`` in PDF + break; + case PPSTRING_BASE16: // hex string, surrounded by ``<`` and ``>`` in PDF + break; + case PPSTRING_BASE85: // base85 string surrounded by ``<~`` and ``~>`` in PDF + break; + } + +The last is actually Postscript specific, not used in PDF, but I think it might appear in contents streams... +No matter how the string is given in PDF (plain or hex), here are two functions to +switch between encoded and decoded strings forms:: + + ppstring ppstring_decoded (ppstring string); // returns decoded string possibly with PDF escapes + ppstring ppstring_encoded (ppstring string); // returns encoded string with no PDF escapes + +For hex strings, encoded form contains hex digits, while decoded form contains arbitrary bytes (the result of hex decoding). +Plain strings usually contains printable ASCII characters, but they might contain any binary data. +As with names, objects parser produces both forms. The raw form with PDF escapes (or raw hex form) is considered the main one. +Eg. when you access ``obj->string`` you always get the encoded form. At any moment you can switch to its alter ego. + +No matter if the string is plain or hex, if its first two bytes (decoded) are UTF16 BOM, the string +is considered unicode. ``ppstring`` object *knows* it is unicode or not:: + + switch (ppstring_utf(string)) + { + case PPSTRING_UTF16LE: // unicode string, utf16le + break; + case PPSTRING_UTF16BE: // unicode string, utf16be + break; + default: // no unicode + } + +Or simply:: + + if (ppstring_utf(string) != 0) { + // handle unicode string + } + +If the string is unicode, BOM remains the part of the string -- ``pplib`` parser does not strip it. +Unicode or not, encoded or decoded, strings are always C-arrays of bytes and ``ppstring_size()`` +always returns the size in bytes. + +Array +----- + +PDF arrays are represented as ``pparray`` type, which is C-array of ``ppobj`` structures. +To get the size:: + + size_t pparray_size(pparray *array) // macro, returns the number of array items + +To get ``ppobj *`` at a given index:: + + ppobj * pparray_at(array, index) // macro, returns ppobj * (no index check) + ppobj * pparray_get(array, index) // macro, returns ppobj * or NULL (with index check) + ppobj * pparray_get_obj (pparray *array, size_t index); // function equiv to pparray_get() + +Iterating over array elements:: + + pparray *array; + size_t index, size; + ppobj *obj; + for (size = pparray_size(array), pparray_first(array, index, obj); index < size; pparray_next(index, obj)) + { + // do something with index and obj + } + +There is no magic first/next macros, just iteration over pointers. One could also use something like:: + + for (index = 0, size = array->size; index < size; ++index) + { + obj = pparray_at(array, index); + // do something with index and obj + } + +When getting values from array and expecting a result of known type, use one of the following:: + + int pparray_get_bool (pparray *array, size_t index, int *v); // get boolean value + int pparray_get_int (pparray *array, size_t index, ppint *v); // get ppint value + int pparray_get_uint (pparray *array, size_t index, ppuint *v); // get ppuint value + int pparray_get_num (pparray *array, size_t index, ppnum *v); // get ppnum value + ppname pparray_get_name (pparray *array, size_t index); // get ppname value + ppstring pparray_get_string (pparray *array, size_t index); // get ppstring value + pparray * pparray_get_array (pparray *array, size_t index); // get pparray * value + ppdict * pparray_get_dict (pparray *array, size_t index); // get ppdict * value + ppref * pparray_get_ref (pparray *array, size_t index); // get ppref * value + +As with ``ppobj_get_*`` suite, numeric types getters set the value of a given type and returns 1, if the type matches. +Otherwise sets nothing and returns 0. Other getters return the value if the type matches, or NULL. + +Every function from ``pparray_get_*`` suite have its ``pparray_rget_*`` counterpart that +that dereferences indirect objects (as explained for ``ppobj_rget_*`` getters). Note that +there is no ``pparray_get_stream()`` function, as streams in PDF are always indirect. +To get the stream from array use:: + + ppstream * pparray_rget_stream (pparray *array, size_t index); + +Dict +---- + +PDF dicts are represented as ``ppdict`` structure, which is C-array of ``ppobj`` with parallel +C-array of ``ppname`` pointers. To get the size of a dict:: + + size_t ppdict_size(ppdict *dict) // macro, returns the number of key-val pairs + +To get the value at a given index (integer):: + + ppobj * ppdict_at(ppdict *dict, index) // macro, no index check + +To get the name (key) at a given index:: + + ppname ppdict_key(ppdict *dict, index) // macro, no index check + +To iterate over dict key-val pairs:: + + ppdict *dict; + ppname *pkey; + ppobj *obj; + + for (ppdict_first(dict, pkey, obj); *pkey != NULL; ppdict_next(pkey, obj)) + { + // do something with *pkey and obj + } + +There is no magic in first/next macros, just iteration through keys and values lists pointers. +For convenient iteration, a list of keys is terminated with NULL, so in the code above ``*pkey != NULL`` +is used as the loop condition. One may also iterate via indices:: + + ppdict *dict; + size_t index, size; + ppname key; + ppobj *obj; + for (index = 0, size = ppdict_size(dict); index < size; ++index) + { + key = ppdict_key(dict, index); + obj = ppdict_at(dict, index); + // do something with key and obj + } + +To get the object associated with a given name, use one of the following:: + + ppobj * ppdict_get_obj (ppdict *dict, const char *name); + int ppdict_get_bool (ppdict *dict, const char *name, int *v); + int ppdict_get_int (ppdict *dict, const char *name, ppint *v); + int ppdict_get_uint (ppdict *dict, const char *name, ppuint *v); + int ppdict_get_num (ppdict *dict, const char *name, ppnum *v); + ppname ppdict_get_name (ppdict *dict, const char *name); + ppstring ppdict_get_string (ppdict *dict, const char *name); + pparray * ppdict_get_array (ppdict *dict, const char *name); + ppdict * ppdict_get_dict (ppdict *dict, const char *name); + ppref * ppdict_get_ref (ppdict *dict, const char *name); + +Note that all getters accepts ``const char *`` as key, so it is ok to say:: + + ppdict_rget_dict(dict, "Resources"); + +as well as:: + + ppdic_rget_dict(dict, name); // ppname name + +Every ``ppdict_get_*`` getter has ``ppdict_rget_*`` counterpart that dereferences +indirect objects if necessary. Note that there is no ``ppdict_get_stream()`` function, +but there is:: + + ppstream * ppdict_rget_stream (ppdict *dict, const char *name); + +So far dicts comes with no names mapping, so by-name dict accessors perform a linear search +through the keys list. PDF dicts are usually small, so it is fast enough. +Building names lookup for every dict in PDF makes no sense I think, as ``pplib`` applications +will query just several dicts I guess.. However, some apps may extensively query +resources, which may refer to hundreds of objects (eg. images). So some mapping for dicts +is still considered. + +Stream +------ + +PDF streams are represented as ``ppstream`` objects. To get the stream dict:: + + ppdict * ppstream_dict(ppstream *stream) // macro + +To read the stream data:: + + uint8_t * ppstream_first (ppstream *stream, size_t *size, int decode); + uint8_t * ppstream_next (ppstream *stream, size_t *size); + void ppstream_done (ppstream *stream); + +Both ``first` and ``next`` functions return a chunk of stream data and sets the ``size`` of the chunk. +``decode`` parameter tell the reader to decompress the stream (1) or return raw (0). A call to ``ppstream_next()`` +must be preceeded by ``ppstream_first()``. Once you're done with the stream, you have to call ``ppstream_done()``, +no matter if the stream has been read to the end or not. The stream data iterator in use:: + + uint8_t *data; + size_t size; + ppstream *stream; + int decode = 1; // 1 - get decompressed, 0 - get raw + + for (data = ppstream_first(stream, &size, decode); data != NULL; data = ppstream_next(stream, &size)) + { + // do something with data and its size + } + ppstream_done(stream); + +Every subsequent iterator call invalidates the previous reader output, so you have to utilize the returned chunk +of data just after you ot that. So the following is wrong:: + + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_next(stream, &size); + data3 = ppstream_next(stream, &size); + some_output(data1, size); + some_output(data2, size); + +The reader calls usually return the same pointer to internal buffer, just filled with a different data. +``pplib`` allocates reasonably large buffer and fills that buffer on subsequent calls to the reader. + +If the source stream has no compression, using both ``decode == 1`` and ``decode == 0`` should give the same result. +You can check if the stream is actually compressed with:: + + ppstream_compressed(stream) // macro, returns non zero if /Filter is present + +It might be necessary to load the entire stream data at once:: + + uint8_t * ppstream_all (ppstream *stream, size_t *size, int decode); + +If the initial buffer size is insufficient, it grows until the entire stream data is loaded. You must call +``ppstream_done(stream)`` after using returned data. + +``ppstream_done()`` doesn't invalidate the stream object, it just closes its internal reader. +The stream itself remains a valid object (eg. one can read it again if necessary), +but the reader buffer is released. It is actually not freed but kept for future the reuse with that on some other stream, +but you still need to mark it ready for reuse to avoid allocating a separate buffer for every stream you're going to read. + +Stream data readers will return ``NULL`` if you haven't close the previous reader process with ``ppstream_done()``. All below is wrong:: + + data1 = ppstream_all(stream, &size, 1); + data2 = ppstream_all(stream, &size, 1); // data2 == NULL + // or + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_first(stream, &size, 1); // data2 == NULL + // or + data1 = ppstream_first(stream, &size, 1); + data2 = ppstream_all(stream, &size, 1); // data2 == NULL + +To avoid unnecessary dependencies, ``pplib`` does not support image filters (``/DCT``, ``/JPX``, ``/JBIG``, ``/CCITT``). +But it is ok to read the stream with ``decode`` set to 1 on such streams. ``pplib`` assumes that the image is the +final/target stream form and just returns it as-is. Eg. in the case of JPEG (``/DCT`` filtered) image both calls should +give the same results:: + + ppstream_all(jpegstream, &jpegsize, 0); // don't decode, return what's there + ppstream_all(jpegstream, &jpegsize, 1); // decode but found image filter, effectively the same + +A bit more about streams memory. As mentioned, ``pplib`` allocates buffers for stream readers. After ``ppstream_done()``, +the stream no longer *owns* the buffer space. But the buffer may remain allocated, to be reused with future readers. +``pplib`` keeps a pool of several buffers. This means, that when you use stream readers, ``pplib`` eats +some memory (1MB or so) that is not freed, even if no streams are used. And even if you free all objects. +If you suffer from this, you can optionally use a pair of functions:: + + void ppstream_init_buffers (void); + void ppstream_free_buffers (void); + +The first initializes buffers pool, unless done so far. Currently ``pplib`` cares of it before opening every stream reader, +so it is not obligatory. The second frees a pool of buffers. The intended use is to call ``ppstream_init_buffers()`` once +as kind of library initializer and to call ``ppstream_free_buffers()`` once, as the library finalizer. + +Filters +------- + +In version v1.00 (20190916) ``ppstream`` API has been extended with filters information. +``ppstream`` knows its filter(s) and keps it as ``stream->filter``:: + + // ppstream *stream; + ppstream_filter *info = &stream->filter; + +``ppstream_filter`` is the following structure:: + + typedef struct { + ppstreamtp *filters; // c-array of filter identifiers (enum integers) + ppdict **params; // c-array of ppdict pointers + size_t count; // number of filters, length of the arrays (typically 1) + } ppstream_filter; + +If ``count > 0`` then ``filters`` member is not NULL. Filters array keeps integer constants:: + + PPSTREAM_BASE16 /* /ASCIIHexDecode */ + PPSTREAM_BASE85 /* /ASCII85Decode */ + PPSTREAM_RUNLENGTH /* /RunLengthDecode */ + PPSTREAM_FLATE /* /FlateDecode */ + PPSTREAM_LZW /* /LZWDecode */ + PPSTREAM_CCITT /* /CCITTFaxDecode */ + PPSTREAM_DCT /* /DCTDecode */ + PPSTREAM_JBIG2 /* /JBIG2Decode */ + PPSTREAM_JPX /* /JPXDecode */ + PPSTREAM_CRYPT /* /Crypt */ + +Params array keeps corresponding filter parameters (``/DecodeParms``) if present. ``params`` member is not NULL +if ``count > 0`` and the stream dict has ``/DecodeParms`` entry. Even if ``params`` is there, +for every N-th filter, ``params[N]`` may be NULL (corresponding to PDF ``null``). + +``stream->filter`` keeps the source stream filter information, which may not correspond to the result of stream readers +(``ppstream_first()``, ``ppstream_next()``, ``ppstream_all()``). The get the filters info relevant to the result from readers:: + + void ppstream_filter_info (ppstream *stream, ppstream_filter *info, int decode); + +The function fills ``ppstream_filter`` structure according to the expected result from stream readers (example 3 shows +how to use it to reconstruct ``/Filter`` and ``/DecodeParms`` when copying the stream to some other PDF). + +To convert filter identifier (``ppstreamtp``) to a corresponding PDF filter name:: + + const char * ppstream_filter_name[]; + +To covert ``ppname`` to filter identifier:: + + int ppstream_filter_type (ppname filtername, ppstreamtp *filtertype); + // returns 1 and sets filtertype if filtername is the proper filter name + +Additional information about the stream can be fetched from macros:: + + ppstream_compressed(stream) /* stream->flags & (PPSTREAM_FILTER|PPSTREAM_IMAGE) */ + ppstream_filtered(stream) /* stream->flags & PPSTREAM_FILTER */ + ppstream_image(stream) /* stream->flags * PPSTREAM_IMAGE */ + +``stream->flags`` is a binary sum of the following:: + + PPSTREAM_FILTER /* set iff the stream filters list has one of: BASE16, BASE85, RUNLENGTH, FLATE, LZW */ + PPSTREAM_IMAGE /* set iff the stream filters list has one of: CCITT, DCT, JBIG2, JPX */ + PPSTREAM_ENCRYPTED /* set iff the stream is encrypted */ + PPSTREAM_ENCRYPTED_OWN /* set iff the stream has own CRYPT filter */ + +Note that ``PPSTREAM_COMPRESSED`` is not there any longer, use ``ppstream_compressed()`` instead. +And there is some more, see ``ppapi.h``. + +Ref +--- + +Indirect objects are represented as ``ppref`` structure. To get the object that the +reference refers to:: + + ppobj * ppref_obj(ppref *ref) // macro + +``ppref`` structure also keeps the reference number and version, a pointer to cross reference table it belongs +to and others, but I guess you won't need anything but the referenced object. ``pplib`` parser resolves references +on-fly. So if there is a dict with indirect objects:: + + << + /Type /Page + /Resources 123 0 R + ... + >> + +the parser will produce ``ppdict`` with ``Resources`` key pointing the proper ``ppref *`` value. +If you need more, access ``ppref`` members:: + + struct ppref { + ppobj object; // target object + ppuint number, version; // identifiers + size_t offset; // file offset (useless for you, may be zero for compressed objects) + ppuint length; // the length of the original object data + ppxref *xref; // cross reference table it belongs to + }; + + +XRef +---- + +Cross reference table is exposed as ``ppxref`` (incomplete type, you can only oprate on its pointer). +To get top document xref:: + + ppxref * ppdoc_xref (ppdoc *pdf); + +To get previous (older) xref:: + + ppxref * ppxref_prev (ppxref *xref); + +To find an object of a given refnumber:: + + ppref * ppxref_find (ppxref *xref, ppuint refnumber); + +[Note: since pplib v0.98 in case of documents with incremental update, ``ppxref_find()`` returns +the newest available version of a given object rather than the object in a given body.] + +PDF +--- + +PDF document is represented as ``ppdoc`` structure (incomplete type, you can only operate on its pointer). +To load a document from file:: + + ppdoc * ppdoc_load (const char *filename); + +To load a document from memory data:: + + ppdoc * ppdoc_mem (const void *data, size_t size); + +The data is assumed to be a buffer allocated with ``malloc`` - it is freed when destroying ``ppdoc``. + +Both loaders returns ``NULL`` on failure. + +To free ``ppdoc`` and all objects it refers to:: + + void ppdoc_free (ppdoc *pdf); + +So far we haven't mention about any explicit object reclaimers. There are no dedicated ``free`` functions +for other objects. You don't allocate or free objects yourself. ``ppdoc`` object is an owner of all +beings it refers to. It also means that every object described so far is alive as long as the containing +``ppdoc`` is alive. + +To access main PDF dicts:: + + ppdict * ppdoc_trailer(ppdoc *pdf); // returns top xref trailer dict + ppdict * ppdoc_catalog(ppdoc *pdf); // returns catalog referred from the trailer + ppdict * ppdoc_info(ppdoc *pdf); // returns info dict referred from the trailer + +To get the PDF version:: + + const char * ppdoc_version_string (ppdoc *pdf); // version string + int ppdoc_version_number (ppdoc *pdf, int *minor); // minor and major numbers + +To get the file size of the source PDF document:: + + size_t ppdoc_file_size (ppdoc *pdf); + +To get the number of objects in all xrefs:: + + ppuint ppdoc_objects (ppdoc *pdf); + +To get the approx usage of memory:: + + size_t ppdoc_memory (ppdoc *pdf, size_t *waste); + +Encryption +---------- + +``pplib`` handles encrypted (password protected) documents. If a document is encrypted, most of strings and streams are ciphered. +In that form they are unreadable and rather useless, you can't even rewrite such strings/streams as-is to a different PDF output. +It is a common practise to *protect* documents with an empty password. Such documents remain readable in Acrobat (just opens them without prompting +for a password), but some features (eg. printing) may restricted by the application. + +When ``pplib`` detects encryption, it follows Acrobat approach and first tries an empty password. If it succeeds, ``pplib`` proceeeds normally, providing +an access to decrypted strings and streams, as if they weren't ciphered. If the document is protected with non-empty password, ``pplib`` gives +a way to provide a password and proceed. Until you provide a password, ``ppdoc`` object returned by ``ppdoc_load()`` function has all object wntries +set to ``null``. + +After loading a document you should check encryption status with:: + + ppcrypt_status ppdoc_crypt_status (ppdoc *pdf); + +``ppcrypt_status`` (integer) may have the following values: + + ``PPCRYPT_NONE`` - no encryption, go ahead + ``PPCRYPT_DONE`` - encryption present but password succeeded, go ahead + ``PPCRYPT_PASS`` - encryption present, need non-empty password + ``PPCRYPT_FAIL`` - invalid or unsupported encryption (eg. undocumented in pdf spec) + +If a password is needed, you can provide one with:: + + ppcrypt_status ppdoc_crypt_pass (ppdoc *pdf, const void *userpass, size_t userpasslength, + const void *ownerpass, size_t ownerpasslength); + +Well, yes, there are actually two passwords in encrypted documents. Relation between them is obscure to me, but enough +to know that having one of them is enough to decrypt the document. If you know the password, you probably mean +``userpass``, in which case you should put ``NULL`` as ``ownerpass``. The function returns ``PPCRYPT_DONE`` if the password +succeeds and the previous status otherwise. Your custom loader function may look like that:: + + ppdoc *pdf; + pdf = ppdoc_load("file.pdf"); + if (pdf == NULL) + return NULL; + switch (ppdoc_crypt_status(pdf)) + { + case PPCRYPT_NONE: + case PPCRYPT_DONE: + return pdf; + case PPCRYPT_PASS: + if (ppdoc_crypt_pass(pdf, "dummy", 5, NULL, 0) == PPCRYPT_DONE || + ppdoc_crypt_pass(pdf, NULL, 0, "dummy", 5) == PPCRYPT_DONE) + return pdf; + printf("sorry, password needed\n"); + ppdoc_free(pdf); + return NULL; + case PPCRYPT_FAIL: + printf("sorry, encryption failed\n"); + ppdoc_free(pdf); + return NULL; + } + +[If you get ``PPCRYPT_FAIL`` it might mean *I failed*, so treat as a bug.] + +If you'd like to know what permissions are given/restricted to encrypted document:: + + ppint ppdoc_permissions (ppdoc *pdf); + +Returned value can be queried with the following binary flags (you can verify with Acrobat *File -> Properties -> Security* tab):: + + PPDOC_ALLOW_PRINT // printing + PPDOC_ALLOW_MODIFY // filling form fields, signing, creating template pages + PPDOC_ALLOW_COPY // copying, copying for accessibility + PPDOC_ALLOW_ANNOTS // filling form fields, copying, signing + PPDOC_ALLOW_EXTRACT // contents copying for accessibility + PPDOC_ALLOW_ASSEMBLY // (no effect) + PPDOC_ALLOW_PRINT_HIRES // (no effect) + +``pplib`` does absolutelly nothing with permissions, it cares only to decrypt the document. As mentioned, encryption applies to strings +and streams. ``pplib`` decrypt strings when parsing document objects, so the result you get is *normal* (not ciphered). +Streams are decrypted whenever you access them. Even if you ask for a raw stream data, you'll get a raw (compressed) stream, but decrypted. +So except the check to ``ppdoc_crypt_status()``, you shouldn't bother about encryption. + +In encrypted documents most of streams are encrypted. To check if a given stream is encrypted:: + + ppstream_encrypted(stream) // macro, returns non-zero if encrypted + +Encryption is independent from compression, don't confuse with ``ppstream_compressed()`` + +Pages +----- + +Several helpers to deal with pages. To get the number of pages:: + + ppuint ppdoc_page_count (ppdoc *pdf); + +To access the root pages tree node:: + + ppref * ppdoc_pages(ppdoc *pdf); + +To get the page reference at a given index:: + + ppref * ppdoc_page (ppdoc *pdf, ppuint index); + +``index`` is a page number. First page has number 1. For index out of bounds ``ppdoc_page()`` returns NULL. +Iterating over pages using index from 1 to ``ppdoc_page_count()`` and calling ``ppdoc_page()`` on each iteration +would be suboptimal. Here is a dedicted iterator for this:: + + ppref * ppdoc_first_page (ppdoc *pdf); + ppref * ppdoc_next_page (ppdoc *pdf); + +The iterator in use:: + + ppdoc *pdf; + ppref *ref; + ppdict *dict; + int pageno; + + pdf = ppdoc_load("file.pdf"); + for (ref = ppdoc_first_page(pdf), pageno = 1; ref != NULL; ref = ppdoc_next_page(pdf), ++pageno) + { + dict = ppref_obj(obj)->dict; // take for granted it is a dict + // do something with the page dict + } + +Functions related to pages return ``ppref *`` ensured to contain dict object, so you don't need sanity +type checks here. + +Contents +-------- + +PDF page contents can be given as a stream or array of streams. Here is a convenience iterator over page +contents streams:: + + ppstream * ppcontents_first (ppdict *dict); + ppstream * ppcontents_next (ppdict *dict, ppstream *stream); + +A complete example of contents stream parser use is given below (example 2). +But before we get there, we need to introduce ``ppcontext`` object. Conceptually, +``ppcontext`` is an owner (memory handler) of objects created on demand (beyond the ``ppdoc``). +So far used only with contents stream parser, which might produce quite some data that we want +to release just after used. To create a new context:: + + pcontext * ppcontext_new (void); + +It initializes a new context and its internal memory heap, taking about 64kB on start. After that, +the context is ready to produce objects (contents parsing functions below). Once objects produced +from a given context are no longer needed:: + + void ppcontext_done (ppcontext *context); + +It restores the context to its initial state, as after ``ppcontext_new()``. It means that the context +is ready to produce another bunch of beings (in the example below, all objects from the next page contents). +Once the context is not needed anymore:: + + void ppcontext_free (ppcontext *context); + +Now, contents stream parser functions take the context as an argument. Iterator form of contents stream parser +that allows to process the contents operator by operator:: + + ppobj * ppcontents_first_op (ppcontext *context, ppstream *stream, size_t *psize, ppname *pname); + ppobj * ppcontents_next_op (ppcontext *context, ppstream *stream, size_t *psize, ppname *pname); + +Returned ``ppobj *`` is a pointer to operands list. ``*psize`` is the number of operands on stack. +The operator itself is stored as ``*pname``. + +To parse the entire contents stream at once with no stop at every operator:: + + ppobj * ppcontents_parse (ppcontext *context, ppstream *stream, size_t *psize); + +Returns probably quite long list of all parsed objects (operands and operatos) in one piece. +The number of objects is stored to ``*psize``. + +[Contents may contain so called inline images, that breaks a simple scheme of operands / operator syntax:: + + BI ID EI + +Contents parser treats this genuine triplet as a single piece, producing two operands (dict and string) +followed by ``EI`` operator name.] + +Boxes +----- + +Boxes (rectangles) in PDF are roughly 4-number arrays, but with a special intent. +``pplib`` provides a basic interface for these special arrays:: + + typedef struct { + ppnum lx, ly, rx, ry; + } pprect; + +This type is used only by helper functions - PDF parser is not aware of the rectangle type. +To convert ``pparray`` to ``pprect``:: + + pprect * pparray_to_rect (pparray *array, pprect *rect); // returns rect or NULL + +In example:: + + pprect rect; + if (pparray_to_rect(array, &rect) != NULL) + ; // do something with rect + +To get some image bounding box:: + + pprect * ppdict_get_rect (ppdict *dict, const char *name, pprect *rect); + // eg. ppdict_get_rect(imagedict, "BBox", &rect) + +To get some page box:: + + pprect * ppdict_get_box (ppdict *dict, const char *name, pprect *rect); + // eg. ppdict_get_box(pagedict, "MediaBox", &rect) + +The later not only checks the pagedict, but also goes through parent page nodes. + +Transforms +---------- + +Transformations are given as 6-number arrays, but with a special intent. +``pplib`` provides a basic interface for these special arrays:: + + typedef struct { + ppnum xx, xy, yx, yy, x, y; + } ppmatrix; + +This type is used only by helper functions - PDF parser is not aware of the matrix type. +To convert ``pparray`` to ``ppmatrix``:: + + ppmatrix * pparray_to_matrix (pparray *array, ppmatrix *matrix); + +In example:: + + ppmatrix matrix; + if (pparray_to_matrix(array, &matrix) != NULL) + ; // do something with matrix + +To get the matrix from dict:: + + ppmatrix * ppdict_get_matrix (ppdict *dict, const char *name, ppmatrix *matrix); + // eg. ppdict_get_matrix(imagedict, "Matrix", &matrix) + +Errors handling +--------------- + +``pplib`` is not verbose, but might happen that it needs to log some error message, eg. when parsing +of some PDF boject fails due to invalid offsets. By default, ``pplib`` prints the message to stdout, eg.:: + + invalid 123 0 R object at offset 123123 + +To replace the default logger, you can provide your own:: + + void pplog_callback (pplogger_callback logger, void *alien); + +``pplogger_callback`` is a function:: + + void your_callback (const char *message, void *alien); + +In example, to redirect messages to stderr you may define a function:: + + void your_callback (const char *message, void *alien) + { + fprintf((FILE *)alien, "\nooops: %s\n", message); + } + +Then set the callback somewhere before loading documents:: + + pplog_callback(your_callback, stderr); + +(example 2 uses that). + +To set the default log messages prefix, eg. ``pplib:``, use:: + + int pplog_prefix (const char *prefix) + +Default is empty. The function succeeds if provided prefix is reasonably short (less then 32 bytes). diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppcode.rst.txt b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppcode.rst.txt new file mode 100644 index 00000000000..ebe92465d80 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppcode.rst.txt @@ -0,0 +1,101 @@ +Examples +======== + +Example 1 +--------- + +.. literalinclude:: ../src/pptest1.c + +Example 2 +--------- + +.. literalinclude:: ../src/pptest2.c + +Example 3 +--------- + +.. literalinclude:: ../src/pptest3.c + +ppapi.h +------- + +.. literalinclude:: ../src/ppapi.h + + +Changes +======= + +v0.97 +----- +First release integrated with luatex sources, plus portability changes from Luigi. + +v0.98 +----- +Changed references resolving in case of incremental updates; tech notes ppxref_find() in ppxref.c. + +v0.99 +----- +Fixed streams handling; null characters should NOT be gobbled after "stream" keyword + +v1.00 +----- +Fixed streams handling (Luigi); object streams updated before other streams +Revised streams handling, ppstream API extended + +v1.01 +----- +Fixed names handling (thanks Hans); digits after '#' weren't skipped + +v1.02 +----- +Fixed page finder (thanks Luigi) + +v1.03 +----- +Fixed TIFF predictor (thanks folks) + +v1.04 +----- +Fixed TIFF predictor for ARM + +v1.05 +----- +Attempt to fix parsing inline images crap + +v2.00 +----- +Deep rework on allocators. +Deep rework on strings and names. + +v2.01 +----- +Fixed invalid stream buffer handling; ``iof_discard()`` no longer reclaims the source (``filter->next``) filter. +Sanity alignment adjustments in ``iof_heap``. + +v2.02 +----- +Fixed incorrect encoding of strings alterego with octal escaping, thanks Luigi. +On Hans request added ``ppdoc_filehandle()`` function and ``ppdoc_file()`` macro for loading ppdoc from ``FILE *``. + +v2.03 +----- +Fixed alloc/free of ``ppdoc`` heap; ``ppdoc`` is now mallocated, no longer taken from its own heap. Again, thanks Luigi. +Fixed warnings about dereferencing type-puned pointers, and some others. + +v2.04 +----- +Byte lookups for names/strings loaders are now int8_t, as char might be signed. +ppdoc_first_page() / ppdoc_next_page() iterator now handles a case when /Kids array is empty. +Fixed generating keys for encrypted streams; ppstring_internal() returns the string of the proper size. +More stream tests in pptest3.c. +Some rework on md5 and sha2. + +v2.05 +----- +uint8_t instead of ppbyte in internals; ppbyte intent is "the most natural 8-bit integer", so it is 'char', +but internally we almost always need uint8_t (char may be signed or not..) + +TODO +==== +- external streams (egzotic) + diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/pplib.rst.txt b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/pplib.rst.txt new file mode 100644 index 00000000000..763dc79cf62 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/pplib.rst.txt @@ -0,0 +1,15 @@ +.. pplib documentation master file, created by + sphinx-quickstart on Thu Jun 07 14:23:51 2018. + You can adapt this file completely to your liking, but it should at least + contain the root `toctree` directive. + +pplib +===== + +.. toctree:: + :maxdepth: 2 + + ppnew + ppapi-2.x + ppapi-1.x + ppcode diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppnew.rst.txt b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppnew.rst.txt new file mode 100644 index 00000000000..4a0a3b42887 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_sources/ppnew.rst.txt @@ -0,0 +1,103 @@ + +1.x vs 2.x +========== + +Allocation +---------- + +Allocation mechanisms has been revised. All objects are still allocated from a private storage (called heap), +but now the heap serves properly aligned memory chunks. Implementation of the heap is (hopefully) platform +independent, so all ``ARM_COMPLIANT`` checks has been removed. Some details work differently on 32/64-bit +machines, this distinction seems inevitable. Allocation related code has been moved to ``util/utilmem*.c`` files. + +[There are actually 3 different allocators - **heap**, **stock**, and **pool** - each of which has 4 variants +for 1, 2, 4 and 8 bytes alignment. So far ``pplib`` uses only the **heap**, but I want to have this part +in a single place for a while. More notes about allocators in ``utilmemallc.h``.] + +``pplib`` uses two heaps: + +* bytes heap - providing 2-bytes aligned memory chunks for byte data +* structures heap - providing 8-bytes aligned chunks for all structures + +2-bytes alignment of byte data is caused by implementation details / limits, ``pplib`` doesn't make a use of it +(could be unaligned as well). All the structures are stored in 8-bytes aligned chunks on both 32 and 64-bit machines +(in some structures we use ``double`` and ``int64_t``, which generally needs 8-bytes). + +Strings And Names +----------------- + +So far, both ``ppname`` and ``ppstring`` were aliases to ``char *`` with an extra structure hidden just below +the data address. The idea was to make a string or name usable whenever chars array can, at the cost of some +pointers trickery. Both names and strings keep an information about pdf-encoded data, as well as plain bytes data. +I implemented this feature once ``pplib 1.0`` was almost done, and to avoid a revolution, I made that with yet +another trick. This all was dirty and caused lots of alignment issues. + +Now ``ppstring`` and ``ppname`` are **structures**, keeping data and size members, pretty much like ``pparray``:: + + struct ppname { + ppbyte *data; + size_t size; + ppname *alterego; + int flags; + }; + + struct ppstring { + ppbyte *data; + size_t size; + ppstring *alterego; + int flags; + }; + +Data member is a pointer to (2-bytes aligned) bytes array -- ``ppbyte *``. ``ppbyte`` is an alias to ``char``. +``pplib`` makes no assumptions about ``ppbyte`` signedness. [I'd prefer to have ``uint8_t``, but better +keep that in sync with ``ppdict_get_*`` suite, which accepts ``char *``. Using ``"string literals"`` +with ``ppdict_get`` function is the most common case, I guess.] + +``ppname_size()`` and ``ppstring_size() `` now have +trivial ``ppname_data()`` and ``ppstring_data()`` counterparts:: + + #define ppname_size(name) ((name)->size) + #define ppname_data(name) ((name)->data) + + #define ppstring_size(string) ((string)->size) + #define ppstring_data(string) ((string)->data) + +Switching between encoded / decoded variants is made via explicit ``alterego`` member. If encoded and decoded forms +are identical, then ``self->alfterego == self`` (never NULL). Helper functions for that:: + + PPAPI ppname * ppname_decoded (ppname *name); + PPAPI ppname * ppname_encoded (ppname *name); + + PPAPI ppbyte * ppname_decoded_data (ppname *name); + PPAPI ppbyte * ppname_encoded_data (ppname *name); + + PPAPI ppstring * ppstring_decoded (ppstring *string); + PPAPI ppstring * ppstring_encoded (ppstring *string); + + PPAPI ppbyte * ppstring_decoded_data (ppstring *string); + PPAPI ppbyte * ppstring_encoded_data (ppstring *string); + +Since ``ppname`` and ``ppstring`` are now structures, all API functions returning name/string or taking name/string +as an argument, now take **a pointer to name/string**. Watch out for ``ppdict_get_*`` functions suite. They still accept +``const char *`` key as an argument, but ``ppname`` type can no longer be used there:: + + ppname key; + ppdict_get_something(dict, key); // wrong + ppdict_get_something(dict, key.data); // ok + + ppname *pkey; + ppdict_get_something(dict, (const char *)pkey); // wrong + ppdict_get_something(dict, pkey->data); // ok + +Consequently, functions / macros that used pointer to ``ppname`` (``ppdict_first()`` / ``ppdict_next()``), +now needs ``ppname **pname``. + +Cleanups +-------- + +Some of unused utils were removed. There is still some code in utils part that is not used by the library, +but I need this tollbox in many other places and don't want to maintain two versions. + +Some unification in integer types; ``size_t`` seems to be the best choice for and integer representing machine +word (``unsigned long`` is not long enough on windows), less utils dependencies, less compiler warnings. + diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/ajax-loader.gif b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/ajax-loader.gif new file mode 100644 index 00000000000..61faf8cab23 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/ajax-loader.gif differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/background_b01.png b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/background_b01.png new file mode 100644 index 00000000000..353f26dde08 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/background_b01.png differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/basic.css b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/basic.css new file mode 100644 index 00000000000..0807176ec0c --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/basic.css @@ -0,0 +1,676 @@ +/* + * basic.css + * ~~~~~~~~~ + * + * Sphinx stylesheet -- basic theme. + * + * :copyright: Copyright 2007-2019 by the Sphinx team, see AUTHORS. + * :license: BSD, see LICENSE for details. + * + */ + +/* -- main layout ----------------------------------------------------------- */ + +div.clearer { + clear: both; +} + +/* -- relbar ---------------------------------------------------------------- */ + +div.related { + width: 100%; + font-size: 90%; +} + +div.related h3 { + display: none; +} + +div.related ul { + margin: 0; + padding: 0 0 0 10px; + list-style: none; +} + +div.related li { + display: inline; +} + +div.related li.right { + float: right; + margin-right: 5px; +} + +/* -- sidebar --------------------------------------------------------------- */ + +div.sphinxsidebarwrapper { + padding: 10px 5px 0 10px; +} + +div.sphinxsidebar { + float: left; + width: 230px; + margin-left: -100%; + font-size: 90%; + word-wrap: break-word; + overflow-wrap : break-word; +} + +div.sphinxsidebar ul { + list-style: none; +} + +div.sphinxsidebar ul ul, +div.sphinxsidebar ul.want-points { + margin-left: 20px; + list-style: square; +} + +div.sphinxsidebar ul ul { + margin-top: 0; + margin-bottom: 0; +} + +div.sphinxsidebar form { + margin-top: 10px; +} + +div.sphinxsidebar input { + border: 1px solid #98dbcc; + font-family: sans-serif; + font-size: 1em; +} + +div.sphinxsidebar #searchbox form.search { + overflow: hidden; +} + +div.sphinxsidebar #searchbox input[type="text"] { + float: left; + width: 80%; + padding: 0.25em; + box-sizing: border-box; +} + +div.sphinxsidebar #searchbox input[type="submit"] { + float: left; + width: 20%; + border-left: none; + padding: 0.25em; + box-sizing: border-box; +} + + +img { + border: 0; + max-width: 100%; +} + +/* -- search page ----------------------------------------------------------- */ + +ul.search { + margin: 10px 0 0 20px; + padding: 0; +} + +ul.search li { + padding: 5px 0 5px 20px; + background-image: url(file.png); + background-repeat: no-repeat; + background-position: 0 7px; +} + +ul.search li a { + font-weight: bold; +} + +ul.search li div.context { + color: #888; + margin: 2px 0 0 30px; + text-align: left; +} + +ul.keywordmatches li.goodmatch a { + font-weight: bold; +} + +/* -- index page ------------------------------------------------------------ */ + +table.contentstable { + width: 90%; + margin-left: auto; + margin-right: auto; +} + +table.contentstable p.biglink { + line-height: 150%; +} + +a.biglink { + font-size: 1.3em; +} + +span.linkdescr { + font-style: italic; + padding-top: 5px; + font-size: 90%; +} + +/* -- general index --------------------------------------------------------- */ + +table.indextable { + width: 100%; +} + +table.indextable td { + text-align: left; + vertical-align: top; +} + +table.indextable ul { + margin-top: 0; + margin-bottom: 0; + list-style-type: none; +} + +table.indextable > tbody > tr > td > ul { + padding-left: 0em; +} + +table.indextable tr.pcap { + height: 10px; +} + +table.indextable tr.cap { + margin-top: 10px; + background-color: #f2f2f2; +} + +img.toggler { + margin-right: 3px; + margin-top: 3px; + cursor: pointer; +} + +div.modindex-jumpbox { + border-top: 1px solid #ddd; + border-bottom: 1px solid #ddd; + margin: 1em 0 1em 0; + padding: 0.4em; +} + +div.genindex-jumpbox { + border-top: 1px solid #ddd; + border-bottom: 1px solid #ddd; + margin: 1em 0 1em 0; + padding: 0.4em; +} + +/* -- domain module index --------------------------------------------------- */ + +table.modindextable td { + padding: 2px; + border-collapse: collapse; +} + +/* -- general body styles --------------------------------------------------- */ + +div.body { + min-width: 450px; + max-width: 800px; +} + +div.body p, div.body dd, div.body li, div.body blockquote { + -moz-hyphens: auto; + -ms-hyphens: auto; + -webkit-hyphens: auto; + hyphens: auto; +} + +a.headerlink { + visibility: hidden; +} + +h1:hover > a.headerlink, +h2:hover > a.headerlink, +h3:hover > a.headerlink, +h4:hover > a.headerlink, +h5:hover > a.headerlink, +h6:hover > a.headerlink, +dt:hover > a.headerlink, +caption:hover > a.headerlink, +p.caption:hover > a.headerlink, +div.code-block-caption:hover > a.headerlink { + visibility: visible; +} + +div.body p.caption { + text-align: inherit; +} + +div.body td { + text-align: left; +} + +.first { + margin-top: 0 !important; +} + +p.rubric { + margin-top: 30px; + font-weight: bold; +} + +img.align-left, .figure.align-left, object.align-left { + clear: left; + float: left; + margin-right: 1em; +} + +img.align-right, .figure.align-right, object.align-right { + clear: right; + float: right; + margin-left: 1em; +} + +img.align-center, .figure.align-center, object.align-center { + display: block; + margin-left: auto; + margin-right: auto; +} + +.align-left { + text-align: left; +} + +.align-center { + text-align: center; +} + +.align-right { + text-align: right; +} + +/* -- sidebars -------------------------------------------------------------- */ + +div.sidebar { + margin: 0 0 0.5em 1em; + border: 1px solid #ddb; + padding: 7px 7px 0 7px; + background-color: #ffe; + width: 40%; + float: right; +} + +p.sidebar-title { + font-weight: bold; +} + +/* -- topics ---------------------------------------------------------------- */ + +div.topic { + border: 1px solid #ccc; + padding: 7px 7px 0 7px; + margin: 10px 0 10px 0; +} + +p.topic-title { + font-size: 1.1em; + font-weight: bold; + margin-top: 10px; +} + +/* -- admonitions ----------------------------------------------------------- */ + +div.admonition { + margin-top: 10px; + margin-bottom: 10px; + padding: 7px; +} + +div.admonition dt { + font-weight: bold; +} + +div.admonition dl { + margin-bottom: 0; +} + +p.admonition-title { + margin: 0px 10px 5px 0px; + font-weight: bold; +} + +div.body p.centered { + text-align: center; + margin-top: 25px; +} + +/* -- tables ---------------------------------------------------------------- */ + +table.docutils { + border: 0; + border-collapse: collapse; +} + +table.align-center { + margin-left: auto; + margin-right: auto; +} + +table caption span.caption-number { + font-style: italic; +} + +table caption span.caption-text { +} + +table.docutils td, table.docutils th { + padding: 1px 8px 1px 5px; + border-top: 0; + border-left: 0; + border-right: 0; + border-bottom: 1px solid #aaa; +} + +table.footnote td, table.footnote th { + border: 0 !important; +} + +th { + text-align: left; + padding-right: 5px; +} + +table.citation { + border-left: solid 1px gray; + margin-left: 1px; +} + +table.citation td { + border-bottom: none; +} + +/* -- figures --------------------------------------------------------------- */ + +div.figure { + margin: 0.5em; + padding: 0.5em; +} + +div.figure p.caption { + padding: 0.3em; +} + +div.figure p.caption span.caption-number { + font-style: italic; +} + +div.figure p.caption span.caption-text { +} + +/* -- field list styles ----------------------------------------------------- */ + +table.field-list td, table.field-list th { + border: 0 !important; +} + +.field-list ul { + margin: 0; + padding-left: 1em; +} + +.field-list p { + margin: 0; +} + +.field-name { + -moz-hyphens: manual; + -ms-hyphens: manual; + -webkit-hyphens: manual; + hyphens: manual; +} + +/* -- hlist styles ---------------------------------------------------------- */ + +table.hlist td { + vertical-align: top; +} + + +/* -- other body styles ----------------------------------------------------- */ + +ol.arabic { + list-style: decimal; +} + +ol.loweralpha { + list-style: lower-alpha; +} + +ol.upperalpha { + list-style: upper-alpha; +} + +ol.lowerroman { + list-style: lower-roman; +} + +ol.upperroman { + list-style: upper-roman; +} + +dl { + margin-bottom: 15px; +} + +dd p { + margin-top: 0px; +} + +dd ul, dd table { + margin-bottom: 10px; +} + +dd { + margin-top: 3px; + margin-bottom: 10px; + margin-left: 30px; +} + +dt:target, span.highlighted { + background-color: #fbe54e; +} + +rect.highlighted { + fill: #fbe54e; +} + +dl.glossary dt { + font-weight: bold; + font-size: 1.1em; +} + +.optional { + font-size: 1.3em; +} + +.sig-paren { + font-size: larger; +} + +.versionmodified { + font-style: italic; +} + +.system-message { + background-color: #fda; + padding: 5px; + border: 3px solid red; +} + +.footnote:target { + background-color: #ffa; +} + +.line-block { + display: block; + margin-top: 1em; + margin-bottom: 1em; +} + +.line-block .line-block { + margin-top: 0; + margin-bottom: 0; + margin-left: 1.5em; +} + +.guilabel, .menuselection { + font-family: sans-serif; +} + +.accelerator { + text-decoration: underline; +} + +.classifier { + font-style: oblique; +} + +abbr, acronym { + border-bottom: dotted 1px; + cursor: help; +} + +/* -- code displays --------------------------------------------------------- */ + +pre { + overflow: auto; + overflow-y: hidden; /* fixes display issues on Chrome browsers */ +} + +span.pre { + -moz-hyphens: none; + -ms-hyphens: none; + -webkit-hyphens: none; + hyphens: none; +} + +td.linenos pre { + padding: 5px 0px; + border: 0; + background-color: transparent; + color: #aaa; +} + +table.highlighttable { + margin-left: 0.5em; +} + +table.highlighttable td { + padding: 0 0.5em 0 0.5em; +} + +div.code-block-caption { + padding: 2px 5px; + font-size: small; +} + +div.code-block-caption code { + background-color: transparent; +} + +div.code-block-caption + div > div.highlight > pre { + margin-top: 0; +} + +div.code-block-caption span.caption-number { + padding: 0.1em 0.3em; + font-style: italic; +} + +div.code-block-caption span.caption-text { +} + +div.literal-block-wrapper { + padding: 1em 1em 0; +} + +div.literal-block-wrapper div.highlight { + margin: 0; +} + +code.descname { + background-color: transparent; + font-weight: bold; + font-size: 1.2em; +} + +code.descclassname { + background-color: transparent; +} + +code.xref, a code { + background-color: transparent; + font-weight: bold; +} + +h1 code, h2 code, h3 code, h4 code, h5 code, h6 code { + background-color: transparent; +} + +.viewcode-link { + float: right; +} + +.viewcode-back { + float: right; + font-family: sans-serif; +} + +div.viewcode-block:target { + margin: -1px -10px; + padding: 0 10px; +} + +/* -- math display ---------------------------------------------------------- */ + +img.math { + vertical-align: middle; +} + +div.body div.math p { + text-align: center; +} + +span.eqno { + float: right; +} + +span.eqno a.headerlink { + position: relative; + left: 0px; + z-index: 1; +} + +div.math:hover a.headerlink { + visibility: visible; +} + +/* -- printout stylesheet --------------------------------------------------- */ + +@media print { + div.document, + div.documentwrapper, + div.bodywrapper { + margin: 0 !important; + width: 100%; + } + + div.sphinxsidebar, + div.related, + div.footer, + #top-link { + display: none; + } +} \ No newline at end of file diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.css b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.css new file mode 100644 index 00000000000..0464a74e637 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.css @@ -0,0 +1,490 @@ +/* + * bizstyle.css_t + * ~~~~~~~~~~~~~~ + * + * Sphinx stylesheet -- business style theme. + * + * :copyright: Copyright 2011-2014 by Sphinx team, see AUTHORS. + * :license: BSD, see LICENSE for details. + * + */ + +@import url("basic.css"); + +/* -- page layout ----------------------------------------------------------- */ + +body { + font-family: 'Lucida Grande', 'Lucida Sans Unicode', 'Geneva', + 'Verdana', sans-serif; + font-size: 14px; + letter-spacing: -0.01em; + line-height: 150%; + text-align: center; + background-color: white; + background-image: url(background_b01.png); + color: black; + padding: 0; + border-right: 1px solid #336699; + border-left: 1px solid #336699; + + margin: 0px 40px 0px 40px; +} + +div.document { + background-color: white; + text-align: left; + background-repeat: repeat-x; + + -moz-box-shadow: 2px 2px 5px #000; + -webkit-box-shadow: 2px 2px 5px #000; +} + +div.bodywrapper { + margin: 0 0 0 240px; + border-left: 1px solid #ccc; +} + +div.body { + margin: 0; + padding: 0.5em 20px 20px 20px; +} + +div.related { + font-size: 1em; + + -moz-box-shadow: 2px 2px 5px #000; + -webkit-box-shadow: 2px 2px 5px #000; +} + +div.related ul { + background-color: #336699; + height: 100%; + overflow: hidden; + border-top: 1px solid #ddd; + border-bottom: 1px solid #ddd; +} + +div.related ul li { + color: white; + margin: 0; + padding: 0; + height: 2em; + float: left; +} + +div.related ul li.right { + float: right; + margin-right: 5px; +} + +div.related ul li a { + margin: 0; + padding: 0 5px 0 5px; + line-height: 1.75em; + color: #fff; +} + +div.related ul li a:hover { + color: #fff; + text-decoration: underline; +} + +div.sphinxsidebarwrapper { + padding: 0; +} + +div.sphinxsidebar { + margin: 0; + padding: 0.5em 12px 12px 12px; + width: 210px; + font-size: 1em; + text-align: left; +} + +div.sphinxsidebar h3, div.sphinxsidebar h4 { + margin: 1em 0 0.5em 0; + font-size: 1em; + padding: 0.1em 0 0.1em 0.5em; + color: white; + border: 1px solid #336699; + background-color: #336699; +} + +div.sphinxsidebar h3 a { + color: white; +} + +div.sphinxsidebar ul { + padding-left: 1.5em; + margin-top: 7px; + padding: 0; + line-height: 130%; +} + +div.sphinxsidebar ul ul { + margin-left: 20px; +} + +div.sphinxsidebar input { + border: 1px solid #336699; +} + +div.footer { + background-color: white; + color: #336699; + padding: 3px 8px 3px 0; + clear: both; + font-size: 0.8em; + text-align: right; + border-bottom: 1px solid #336699; + + -moz-box-shadow: 2px 2px 5px #000; + -webkit-box-shadow: 2px 2px 5px #000; +} + +div.footer a { + color: #336699; + text-decoration: underline; +} + +/* -- body styles ----------------------------------------------------------- */ + +p { + margin: 0.8em 0 0.5em 0; +} + +a { + color: #336699; + text-decoration: none; +} + +a:hover { + color: #336699; + text-decoration: underline; +} + +div.body a { + text-decoration: underline; +} + +h1, h2, h3 { + color: #336699; +} + +h1 { + margin: 0; + padding: 0.7em 0 0.3em 0; + font-size: 1.5em; +} + +h2 { + margin: 1.3em 0 0.2em 0; + font-size: 1.35em; + padding-bottom: .5em; + border-bottom: 1px solid #336699; +} + +h3 { + margin: 1em 0 -0.3em 0; + font-size: 1.2em; + padding-bottom: .3em; + border-bottom: 1px solid #CCCCCC; +} + +div.body h1 a, div.body h2 a, div.body h3 a, +div.body h4 a, div.body h5 a, div.body h6 a { + color: black!important; +} + +h1 a.anchor, h2 a.anchor, h3 a.anchor, +h4 a.anchor, h5 a.anchor, h6 a.anchor { + display: none; + margin: 0 0 0 0.3em; + padding: 0 0.2em 0 0.2em; + color: #aaa!important; +} + +h1:hover a.anchor, h2:hover a.anchor, h3:hover a.anchor, h4:hover a.anchor, +h5:hover a.anchor, h6:hover a.anchor { + display: inline; +} + +h1 a.anchor:hover, h2 a.anchor:hover, h3 a.anchor:hover, h4 a.anchor:hover, +h5 a.anchor:hover, h6 a.anchor:hover { + color: #777; + background-color: #eee; +} + +a.headerlink { + color: #c60f0f!important; + font-size: 1em; + margin-left: 6px; + padding: 0 4px 0 4px; + text-decoration: none!important; +} + +a.headerlink:hover { + background-color: #ccc; + color: white!important; +} + +cite, code, tt { + font-family: 'Consolas', 'Deja Vu Sans Mono', + 'Bitstream Vera Sans Mono', monospace; + font-size: 0.95em; + letter-spacing: 0.01em; +} + +code { + background-color: #F2F2F2; + border-bottom: 1px solid #ddd; + color: #333; +} + +code.descname, code.descclassname, code.xref { + border: 0; +} + +hr { + border: 1px solid #abc; + margin: 2em; +} + +a code { + border: 0; + color: #CA7900; +} + +a code:hover { + color: #2491CF; +} + +pre { + background-color: transparent !important; + font-family: 'Consolas', 'Deja Vu Sans Mono', + 'Bitstream Vera Sans Mono', monospace; + font-size: 0.95em; + letter-spacing: 0.015em; + line-height: 120%; + padding: 0.5em; + border-right: 5px solid #ccc; + border-left: 5px solid #ccc; +} + +pre a { + color: inherit; + text-decoration: underline; +} + +td.linenos pre { + padding: 0.5em 0; +} + +div.quotebar { + background-color: #f8f8f8; + max-width: 250px; + float: right; + padding: 2px 7px; + border: 1px solid #ccc; +} + +div.topic { + background-color: #f8f8f8; +} + +table { + border-collapse: collapse; + margin: 0 -0.5em 0 -0.5em; +} + +table td, table th { + padding: 0.2em 0.5em 0.2em 0.5em; +} + +div.admonition { + font-size: 0.9em; + margin: 1em 0 1em 0; + border: 3px solid #cccccc; + background-color: #f7f7f7; + padding: 0; +} + +div.admonition p { + margin: 0.5em 1em 0.5em 1em; + padding: 0; +} + +div.admonition li p { + margin-left: 0; +} + +div.admonition pre, div.warning pre { + margin: 0; +} + +div.highlight { + margin: 0.4em 1em; +} + +div.admonition p.admonition-title { + margin: 0; + padding: 0.1em 0 0.1em 0.5em; + color: white; + border-bottom: 3px solid #cccccc; + font-weight: bold; + background-color: #165e83; +} + +div.danger { border: 3px solid #f0908d; background-color: #f0cfa0; } +div.error { border: 3px solid #f0908d; background-color: #ede4cd; } +div.warning { border: 3px solid #f8b862; background-color: #f0cfa0; } +div.caution { border: 3px solid #f8b862; background-color: #ede4cd; } +div.attention { border: 3px solid #f8b862; background-color: #f3f3f3; } +div.important { border: 3px solid #f0cfa0; background-color: #ede4cd; } +div.note { border: 3px solid #f0cfa0; background-color: #f3f3f3; } +div.hint { border: 3px solid #bed2c3; background-color: #f3f3f3; } +div.tip { border: 3px solid #bed2c3; background-color: #f3f3f3; } + +div.danger p.admonition-title, div.error p.admonition-title { + background-color: #b7282e; + border-bottom: 3px solid #f0908d; +} + +div.caution p.admonition-title, +div.warning p.admonition-title, +div.attention p.admonition-title { + background-color: #f19072; + border-bottom: 3px solid #f8b862; +} + +div.note p.admonition-title, div.important p.admonition-title { + background-color: #f8b862; + border-bottom: 3px solid #f0cfa0; +} + +div.hint p.admonition-title, div.tip p.admonition-title { + background-color: #7ebea5; + border-bottom: 3px solid #bed2c3; +} + +div.admonition ul, div.admonition ol, +div.warning ul, div.warning ol { + margin: 0.1em 0.5em 0.5em 3em; + padding: 0; +} + +div.versioninfo { + margin: 1em 0 0 0; + border: 1px solid #ccc; + background-color: #DDEAF0; + padding: 8px; + line-height: 1.3em; + font-size: 0.9em; +} + +.viewcode-back { + font-family: 'Lucida Grande', 'Lucida Sans Unicode', 'Geneva', + 'Verdana', sans-serif; +} + +div.viewcode-block:target { + background-color: #f4debf; + border-top: 1px solid #ac9; + border-bottom: 1px solid #ac9; +} + +p.versionchanged span.versionmodified { + font-size: 0.9em; + margin-right: 0.2em; + padding: 0.1em; + background-color: #DCE6A0; +} + +/* -- table styles ---------------------------------------------------------- */ + +table.docutils { + margin: 1em 0; + padding: 0; + border: 1px solid white; + background-color: #f7f7f7; +} + +table.docutils td, table.docutils th { + padding: 1px 8px 1px 5px; + border-top: 0; + border-left: 0; + border-right: 1px solid white; + border-bottom: 1px solid white; +} + +table.docutils td p { + margin-top: 0; + margin-bottom: 0.3em; +} + +table.field-list td, table.field-list th { + border: 0 !important; + word-break: break-word; +} + +table.footnote td, table.footnote th { + border: 0 !important; +} + +th { + color: white; + text-align: left; + padding-right: 5px; + background-color: #82A0BE; +} + +div.literal-block-wrapper div.code-block-caption { + background-color: #EEE; + border-style: solid; + border-color: #CCC; + border-width: 1px 5px; +} + +/* WIDE DESKTOP STYLE */ +@media only screen and (min-width: 1176px) { +body { + margin: 0 40px 0 40px; +} +} + +/* TABLET STYLE */ +@media only screen and (min-width: 768px) and (max-width: 991px) { +body { + margin: 0 40px 0 40px; +} +} + +/* MOBILE LAYOUT (PORTRAIT/320px) */ +@media only screen and (max-width: 767px) { +body { + margin: 0; +} +div.bodywrapper { + margin: 0; + width: 100%; + border: none; +} +div.sphinxsidebar { + display: none; +} +} + +/* MOBILE LAYOUT (LANDSCAPE/480px) */ +@media only screen and (min-width: 480px) and (max-width: 767px) { +body { + margin: 0 20px 0 20px; +} +} + +/* RETINA OVERRIDES */ +@media +only screen and (-webkit-min-device-pixel-ratio: 2), +only screen and (min-device-pixel-ratio: 2) { +} + +/* -- end ------------------------------------------------------------------- */ \ No newline at end of file diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.js b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.js new file mode 100644 index 00000000000..6614fe388d1 --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/bizstyle.js @@ -0,0 +1,41 @@ +// +// bizstyle.js +// ~~~~~~~~~~~ +// +// Sphinx javascript -- for bizstyle theme. +// +// This theme was created by referring to 'sphinxdoc' +// +// :copyright: Copyright 2012-2014 by Sphinx team, see AUTHORS. +// :license: BSD, see LICENSE for details. +// +$(document).ready(function(){ + if (navigator.userAgent.indexOf('iPhone') > 0 || + navigator.userAgent.indexOf('Android') > 0) { + $("li.nav-item-0 a").text("Top"); + } + + $("div.related:first ul li:not(.right) a").slice(1).each(function(i, item){ + if (item.text.length > 20) { + var tmpstr = item.text + $(item).attr("title", tmpstr); + $(item).text(tmpstr.substr(0, 17) + "..."); + } + }); + $("div.related:last ul li:not(.right) a").slice(1).each(function(i, item){ + if (item.text.length > 20) { + var tmpstr = item.text + $(item).attr("title", tmpstr); + $(item).text(tmpstr.substr(0, 17) + "..."); + } + }); +}); + +$(window).resize(function(){ + if ($(window).width() <= 776) { + $("li.nav-item-0 a").text("Top"); + } + else { + $("li.nav-item-0 a").text("pplib 0.1 documentation"); + } +}); \ No newline at end of file diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-bright.png b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-bright.png new file mode 100644 index 00000000000..15e27edb12a Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-bright.png differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-close.png b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-close.png new file mode 100644 index 00000000000..4d91bcf57de Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment-close.png differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment.png b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment.png new file mode 100644 index 00000000000..dfbc0cbd512 Binary files /dev/null and b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/comment.png differ diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries.js b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries.js new file mode 100644 index 00000000000..59735f59dcb --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries.js @@ -0,0 +1 @@ +if(typeof Object.create!=="function"){Object.create=function(e){function t(){}t.prototype=e;return new t}}var ua={toString:function(){return navigator.userAgent},test:function(e){return this.toString().toLowerCase().indexOf(e.toLowerCase())>-1}};ua.version=(ua.toString().toLowerCase().match(/[\s\S]+(?:rv|it|ra|ie)[\/: ]([\d.]+)/)||[])[1];ua.webkit=ua.test("webkit");ua.gecko=ua.test("gecko")&&!ua.webkit;ua.opera=ua.test("opera");ua.ie=ua.test("msie")&&!ua.opera;ua.ie6=ua.ie&&document.compatMode&&typeof document.documentElement.style.maxHeight==="undefined";ua.ie7=ua.ie&&document.documentElement&&typeof document.documentElement.style.maxHeight!=="undefined"&&typeof XDomainRequest==="undefined";ua.ie8=ua.ie&&typeof XDomainRequest!=="undefined";var domReady=function(){var e=[];var t=function(){if(!arguments.callee.done){arguments.callee.done=true;for(var t=0;t=200&&r.status<300||r.status===304||navigator.userAgent.indexOf("Safari")>-1&&typeof r.status==="undefined"){t(r.responseText)}else{n()}document.documentElement.style.cursor="";r=null}};r.send("")};var l=function(t){t=t.replace(e.REDUNDANT_COMPONENTS,"");t=t.replace(e.REDUNDANT_WHITESPACE,"$1");t=t.replace(e.WHITESPACE_IN_PARENTHESES,"($1)");t=t.replace(e.MORE_WHITESPACE," ");t=t.replace(e.FINAL_SEMICOLONS,"}");return t};var c={stylesheet:function(t){var n={};var r=[],i=[],s=[],o=[];var u=t.cssHelperText;var a=t.getAttribute("media");if(a){var f=a.toLowerCase().split(",")}else{var f=["all"]}for(var l=0;l-1&&a.href&&a.href.length!==0&&!a.disabled){r[r.length]=a}}if(r.length>0){var c=0;var d=function(){c++;if(c===r.length){i()}};var v=function(t){var n=t.href;f(n,function(r){r=l(r).replace(e.RELATIVE_URLS,"url("+n.substring(0,n.lastIndexOf("/"))+"/$1)");t.cssHelperText=r;d()},d)};for(u=0;u0){r.setAttribute("media",t.join(","))}document.getElementsByTagName("head")[0].appendChild(r);if(r.styleSheet){r.styleSheet.cssText=e}else{r.appendChild(document.createTextNode(e))}r.addedWithCssHelper=true;if(typeof n==="undefined"||n===true){cssHelper.parsed(function(t){var n=p(r,e);for(var i in n){if(n.hasOwnProperty(i)){g(i,n[i])}}a("newStyleParsed",r)})}else{r.parsingDisallowed=true}return r},removeStyle:function(e){return e.parentNode.removeChild(e)},parsed:function(e){if(n){s(e)}else{if(typeof t!=="undefined"){if(typeof e==="function"){e(t)}}else{s(e);d()}}},stylesheets:function(e){cssHelper.parsed(function(t){e(m.stylesheets||y("stylesheets"))})},mediaQueryLists:function(e){cssHelper.parsed(function(t){e(m.mediaQueryLists||y("mediaQueryLists"))})},rules:function(e){cssHelper.parsed(function(t){e(m.rules||y("rules"))})},selectors:function(e){cssHelper.parsed(function(t){e(m.selectors||y("selectors"))})},declarations:function(e){cssHelper.parsed(function(t){e(m.declarations||y("declarations"))})},properties:function(e){cssHelper.parsed(function(t){e(m.properties||y("properties"))})},broadcast:a,addListener:function(e,t){if(typeof t==="function"){if(!u[e]){u[e]={listeners:[]}}u[e].listeners[u[e].listeners.length]=t}},removeListener:function(e,t){if(typeof t==="function"&&u[e]){var n=u[e].listeners;for(var r=0;r=a||s&&l0}}else if("device-height"===e.substring(r-13,r)){c=screen.height;if(t!==null){if(u==="length"){return i&&c>=a||s&&c0}}else if("width"===e.substring(r-5,r)){l=document.documentElement.clientWidth||document.body.clientWidth;if(t!==null){if(u==="length"){return i&&l>=a||s&&l0}}else if("height"===e.substring(r-6,r)){c=document.documentElement.clientHeight||document.body.clientHeight;if(t!==null){if(u==="length"){return i&&c>=a||s&&c0}}else if("device-aspect-ratio"===e.substring(r-19,r)){return u==="aspect-ratio"&&screen.width*a[1]===screen.height*a[0]}else if("color-index"===e.substring(r-11,r)){var h=Math.pow(2,screen.colorDepth);if(t!==null){if(u==="absolute"){return i&&h>=a||s&&h0}}else if("color"===e.substring(r-5,r)){var p=screen.colorDepth;if(t!==null){if(u==="absolute"){return i&&p>=a||s&&p0}}else if("resolution"===e.substring(r-10,r)){var d;if(f==="dpcm"){d=o("1cm")}else{d=o("1in")}if(t!==null){if(u==="resolution"){return i&&d>=a||s&&d0}}else{return false}};var a=function(e){var t=e.getValid();var n=e.getExpressions();var r=n.length;if(r>0){for(var i=0;i0){u=false;for(var f=0;f0){l[c++]=","}l[c++]=h}}if(l.length>0){r[r.length]=cssHelper.addStyle("@media "+l.join("")+"{"+e.getCssText()+"}",t,false)}};var l=function(e,t){for(var n=0;n0}}var o=[],u=[];for(var f in i){if(i.hasOwnProperty(f)){o[o.length]=f;if(i[f]){u[u.length]=f}if(f==="all"){n=true}}}if(u.length>0){r[r.length]=cssHelper.addStyle(e.getCssText(),u,false)}var c=e.getMediaQueryLists();if(n){l(c)}else{l(c,o)}};var h=function(e){for(var t=0;td||Math.abs(s-t)>d){e=n;t=s;clearTimeout(r);r=setTimeout(function(){if(!i()){p()}else{cssHelper.broadcast("cssMediaQueriesTested")}},500)}};window.onresize=function(){var e=window.onresize||function(){};return function(){e();s()}}()};var m=document.documentElement;m.style.marginLeft="-32767px";setTimeout(function(){m.style.marginLeft=""},5e3);return function(){if(!i()){cssHelper.addListener("newStyleParsed",function(e){c(e.cssHelperParsed.stylesheet)});cssHelper.addListener("cssMediaQueriesTested",function(){if(ua.ie){m.style.width="1px"}setTimeout(function(){m.style.width="";m.style.marginLeft=""},0);cssHelper.removeListener("cssMediaQueriesTested",arguments.callee)});s();p()}else{m.style.marginLeft=""}v()}}());try{document.execCommand("BackgroundImageCache",false,true)}catch(e){} diff --git a/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries_src.js b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries_src.js new file mode 100644 index 00000000000..f21dd4949aa --- /dev/null +++ b/Build/source/texk/web2c/luatexdir/luapplib/doc/_build/html/_static/css3-mediaqueries_src.js @@ -0,0 +1,1104 @@ +/* +css3-mediaqueries.js - CSS Helper and CSS3 Media Queries Enabler + +author: Wouter van der Graaf +version: 1.0 (20110330) +license: MIT +website: http://code.google.com/p/css3-mediaqueries-js/ + +W3C spec: http://www.w3.org/TR/css3-mediaqueries/ + +Note: use of embedded