summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKarl Berry <karl@freefriends.org>2023-08-20 19:54:11 +0000
committerKarl Berry <karl@freefriends.org>2023-08-20 19:54:11 +0000
commitcfc28e1384ddc5bcce439c263230f1fbb4a32a92 (patch)
tree1151593359aaa1e765d8226e0078c3897fbb7592
parent287a8aba69a5e806a7b0f04caa037daf2c0a2db3 (diff)
lualibs (20aug23)
git-svn-id: svn://tug.org/texlive/trunk@67994 c570f23f-e606-0410-a88d-b1316a301751
-rw-r--r--Master/texmf-dist/doc/luatex/lualibs/NEWS3
-rw-r--r--Master/texmf-dist/doc/luatex/lualibs/README.md6
-rw-r--r--Master/texmf-dist/doc/luatex/lualibs/lualibs.pdfbin81128 -> 82357 bytes
-rw-r--r--Master/texmf-dist/source/luatex/lualibs/lualibs.dtx18
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-basic-merged.lua66
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-basic.lua4
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-dir.lua40
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-extended-merged.lua271
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-extended.lua4
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-file.lua22
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-string.lua24
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-unicode.lua1
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-util-dim.lua234
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-util-prs.lua27
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-util-sac.lua12
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-util-str.lua5
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-util-tab.lua2
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs-util-zip.lua363
-rw-r--r--Master/texmf-dist/tex/luatex/lualibs/lualibs.lua4
19 files changed, 738 insertions, 368 deletions
diff --git a/Master/texmf-dist/doc/luatex/lualibs/NEWS b/Master/texmf-dist/doc/luatex/lualibs/NEWS
index 889232dc47a..6117812375e 100644
--- a/Master/texmf-dist/doc/luatex/lualibs/NEWS
+++ b/Master/texmf-dist/doc/luatex/lualibs/NEWS
@@ -1,4 +1,7 @@
History of the lualibs package
+2023/07/13 v2.76/
+ * sync with Context current as of 2023/07/13.
+
2022/10/04 v2.75/
* sync with Context current as of 2022/10/04.
* add util-sac
diff --git a/Master/texmf-dist/doc/luatex/lualibs/README.md b/Master/texmf-dist/doc/luatex/lualibs/README.md
index 09194115ceb..f4f2e7162ce 100644
--- a/Master/texmf-dist/doc/luatex/lualibs/README.md
+++ b/Master/texmf-dist/doc/luatex/lualibs/README.md
@@ -1,10 +1,10 @@
# The Lualibs Package
-VERSION: 2.75
+VERSION: 2.76
-DATE: 2022-10-04
+DATE: 2023-07-13
-FONTLOADERDATE: 2022-10-04
+FONTLOADERDATE: 2023-07-13
Lualibs is a collection of Lua modules useful for general programming.
diff --git a/Master/texmf-dist/doc/luatex/lualibs/lualibs.pdf b/Master/texmf-dist/doc/luatex/lualibs/lualibs.pdf
index 175e7e9f017..00ef113d5f8 100644
--- a/Master/texmf-dist/doc/luatex/lualibs/lualibs.pdf
+++ b/Master/texmf-dist/doc/luatex/lualibs/lualibs.pdf
Binary files differ
diff --git a/Master/texmf-dist/source/luatex/lualibs/lualibs.dtx b/Master/texmf-dist/source/luatex/lualibs/lualibs.dtx
index ebdba58424f..d0335005278 100644
--- a/Master/texmf-dist/source/luatex/lualibs/lualibs.dtx
+++ b/Master/texmf-dist/source/luatex/lualibs/lualibs.dtx
@@ -37,7 +37,7 @@
\input docstrip.tex
\Msg{************************************************************************}
\Msg{* Installation}
-\Msg{* Package: lualibs 2022-10-04 v2.75 Lua additional functions.}
+\Msg{* Package: lualibs 2023-07-13 v2.76 Lua additional functions.}
\Msg{************************************************************************}
\keepsilent
@@ -107,7 +107,7 @@ and lualibs-extended.lua.
%<*driver>
\NeedsTeXFormat{LaTeX2e}
\ProvidesFile{lualibs.drv}
- [2022/10/04 v2.75 Lua Libraries.]
+ [2023/07/13 v2.76 Lua Libraries.]
\documentclass{ltxdoc}
\usepackage{fancyvrb,xspace}
\usepackage[x11names]{xcolor}
@@ -208,7 +208,7 @@ and lualibs-extended.lua.
% \GetFileInfo{lualibs.drv}
%
% \title{The \identifier{lualibs} package}
-% \date{2022/10/04 v2.75}
+% \date{2023/07/13 v2.76}
% \author{Élie Roux · \email{elie.roux@telecom-bretagne.eu}\\
% Philipp Gesang · \email{phg@phi-gamma.net}\\
% The \LaTeX{} Project · \email{https://github.com/latex3/lualibs/}\\
@@ -430,8 +430,8 @@ lualibs = lualibs or { }
lualibs.module_info = {
name = "lualibs",
- version = "2.75", --TAGVERSION
- date = "2022-10-04", --TAGDATE
+ version = "2.76", --TAGVERSION
+ date = "2023-07-13", --TAGDATE
description = "ConTeXt Lua standard libraries.",
author = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
copyright = "PRAGMA ADE / ConTeXt Development Team",
@@ -584,8 +584,8 @@ local loadmodule = lualibs.loadmodule
local lualibs_basic_module = {
name = "lualibs-basic",
- version = "2.75", --TAGVERSION
- date = "2022-10-04", --TAGDATE
+ version = "2.76", --TAGVERSION
+ date = "2023-07-13", --TAGDATE
description = "ConTeXt Lua libraries -- basic collection.",
author = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
copyright = "PRAGMA ADE / ConTeXt Development Team",
@@ -665,8 +665,8 @@ lualibs = lualibs or { }
local lualibs_extended_module = {
name = "lualibs-extended",
- version = "2.75", --TAGVERSION
- date = "2022-10-04", --TAGDATE
+ version = "2.76", --TAGVERSION
+ date = "2023-07-13", --TAGDATE
description = "ConTeXt Lua libraries -- extended collection.",
author = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
copyright = "PRAGMA ADE / ConTeXt Development Team",
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic-merged.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic-merged.lua
index 690a3160acb..b201cfab041 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic-merged.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic-merged.lua
@@ -1,6 +1,6 @@
-- merged file : lualibs-basic-merged.lua
-- parent file : lualibs-basic.lua
--- merge date : 2022-10-04 17:16
+-- merge date : 2023-07-13 12:55
do -- begin closure to overcome local limits and interference
@@ -1274,7 +1274,7 @@ if not modules then modules={} end modules ['l-string']={
license="see context related readme files"
}
local string=string
-local sub,gmatch,format,char,byte,rep,lower=string.sub,string.gmatch,string.format,string.char,string.byte,string.rep,string.lower
+local sub,gmatch,format,char,byte,rep,lower,find=string.sub,string.gmatch,string.format,string.char,string.byte,string.rep,string.lower,string.find
local lpegmatch,patterns=lpeg.match,lpeg.patterns
local P,S,C,Ct,Cc,Cs=lpeg.P,lpeg.S,lpeg.C,lpeg.Ct,lpeg.Cc,lpeg.Cs
local unquoted=patterns.squote*C(patterns.nosquote)*patterns.squote+patterns.dquote*C(patterns.nodquote)*patterns.dquote
@@ -1284,10 +1284,18 @@ end
function string.quoted(str)
return format("%q",str)
end
-function string.count(str,pattern)
+function string.count(str,pattern)
local n=0
- for _ in gmatch(str,pattern) do
- n=n+1
+ local i=1
+ local l=#pattern
+ while true do
+ i=find(str,pattern,i)
+ if i then
+ n=n+1
+ i=i+l
+ else
+ break
+ end
end
return n
end
@@ -4022,9 +4030,23 @@ function file.withinbase(path)
end
return true
end
-local symlinkattributes=lfs.symlinkattributes
-function lfs.readlink(name)
- return symlinkattributes(name,"target") or nil
+do
+ local symlinktarget=lfs.symlinktarget
+ local symlinkattributes=lfs.symlinkattributes
+ if symlinktarget then
+ function lfs.readlink(name)
+ local target=symlinktarget(name)
+ return name~=target and name or nil
+ end
+ elseif symlinkattributes then
+ function lfs.readlink(name)
+ return symlinkattributes(name,"target") or nil
+ end
+ else
+ function lfs.readlink(name)
+ return nil
+ end
+ end
end
end -- closure
@@ -4136,7 +4158,7 @@ dir=dir or {}
local dir=dir
local lfs=lfs
local attributes=lfs.attributes
-local walkdir=lfs.dir
+local scandir=lfs.dir
local isdir=lfs.isdir
local isfile=lfs.isfile
local currentdir=lfs.currentdir
@@ -4167,6 +4189,15 @@ else
lfs.isdir=isdir
lfs.isfile=isfile
end
+local isreadable=file.isreadable
+local walkdir=function(p,...)
+ if isreadable(p.."/.") then
+ return scandir(p,...)
+ else
+ return function() end
+ end
+end
+lfs.walkdir=walkdir
function dir.current()
return (gsub(currentdir(),"\\","/"))
end
@@ -4582,6 +4613,23 @@ do
return str
end
end
+ function dir.expandlink(dir,report)
+ local curdir=currentdir()
+ local trace=type(report)=="function"
+ if chdir(dir) then
+ local newdir=currentdir()
+ if newdir~=dir and trace then
+ report("following symlink %a to %a",dir,newdir)
+ end
+ chdir(curdir)
+ return newdir
+ else
+ if trace then
+ report("unable to check path %a",dir)
+ end
+ return dir
+ end
+ end
end
file.expandname=dir.expandname
local stack={}
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic.lua
index d578f70de0b..570a1f4564c 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-basic.lua
@@ -29,8 +29,8 @@ local loadmodule = lualibs.loadmodule
local lualibs_basic_module = {
name = "lualibs-basic",
- version = "2.75", --TAGVERSION
- date = "2022-10-04", --TAGDATE
+ version = "2.76", --TAGVERSION
+ date = "2023-07-13", --TAGDATE
description = "ConTeXt Lua libraries -- basic collection.",
author = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
copyright = "PRAGMA ADE / ConTeXt Development Team",
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-dir.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-dir.lua
index ac8e2f4e8e1..3164068505d 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-dir.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-dir.lua
@@ -21,7 +21,8 @@ local dir = dir
local lfs = lfs
local attributes = lfs.attributes
-local walkdir = lfs.dir
+----- walkdir = lfs.dir
+local scandir = lfs.dir
local isdir = lfs.isdir -- not robust, will be overloaded anyway
local isfile = lfs.isfile -- not robust, will be overloaded anyway
local currentdir = lfs.currentdir
@@ -69,6 +70,20 @@ else
end
+-- safeguard
+
+local isreadable = file.isreadable
+
+local walkdir = function(p,...)
+ if isreadable(p.."/.") then
+ return scandir(p,...)
+ else
+ return function() end
+ end
+end
+
+lfs.walkdir = walkdir
+
-- handy
function dir.current()
@@ -197,7 +212,7 @@ local function collectpattern(path,patt,recurse,result)
if not find(path,"/$") then
path = path .. '/'
end
- for name in scanner, first do -- cna be optimized
+ for name in scanner, first do -- can be optimized
if name == "." then
-- skip
elseif name == ".." then
@@ -596,6 +611,27 @@ do
end
+ -- This go there anc check works okay in tricky situation as we encounter
+ -- on osx, where tex installations use rather complex chains of links.
+
+ function dir.expandlink(dir,report)
+ local curdir = currentdir()
+ local trace = type(report) == "function"
+ if chdir(dir) then
+ local newdir = currentdir()
+ if newdir ~= dir and trace then
+ report("following symlink %a to %a",dir,newdir)
+ end
+ chdir(curdir)
+ return newdir
+ else
+ if trace then
+ report("unable to check path %a",dir)
+ end
+ return dir
+ end
+ end
+
end
file.expandname = dir.expandname -- for convenience
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended-merged.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended-merged.lua
index 08428c51ac5..ceecbf30132 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended-merged.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended-merged.lua
@@ -1,6 +1,6 @@
-- merged file : lualibs-extended-merged.lua
-- parent file : lualibs-extended.lua
--- merge date : 2022-10-04 17:16
+-- merge date : 2023-07-13 12:55
do -- begin closure to overcome local limits and interference
@@ -481,13 +481,13 @@ if bit32 and not streams.tocardinal1 then
local extract=bit32.extract
local char=string.char
streams.tocardinal1=char
- function streams.tocardinal2(n) return char(extract(8,8),extract(0,8)) end
- function streams.tocardinal3(n) return char(extract(16,8),extract(8,8),extract(0,8)) end
- function streams.tocardinal4(n) return char(extract(24,8),extract(16,8),extract(8,8),extract(0,8)) end
+ function streams.tocardinal2(n) return char(extract(n,8,8),extract(n,0,8)) end
+ function streams.tocardinal3(n) return char(extract(n,16,8),extract(n,8,8),extract(n,0,8)) end
+ function streams.tocardinal4(n) return char(extract(n,24,8),extract(n,16,8),extract(n,8,8),extract(n,0,8)) end
streams.tocardinal1le=char
- function streams.tocardinal2le(n) return char(extract(0,8),extract(8,8)) end
- function streams.tocardinal3le(n) return char(extract(0,8),extract(8,8),extract(16,8)) end
- function streams.tocardinal4le(n) return char(extract(0,8),extract(8,8),extract(16,8),extract(24,8)) end
+ function streams.tocardinal2le(n) return char(extract(n,0,8),extract(n,8,8)) end
+ function streams.tocardinal3le(n) return char(extract(n,0,8),extract(n,8,8),extract(n,16,8)) end
+ function streams.tocardinal4le(n) return char(extract(n,0,8),extract(n,8,8),extract(n,16,8),extract(n,24,8)) end
end
if not streams.readcstring then
local readchar=streams.readchar
@@ -701,6 +701,7 @@ local p_prune_intospace=Cs (noleading*(notrailing+intospace+1 )^0 )
local p_retain_normal=Cs ((normalline+normalempty )^0 )
local p_retain_collapse=Cs ((normalline+doubleempty )^0 )
local p_retain_noempty=Cs ((normalline+singleempty )^0 )
+local p_collapse_all=Cs (stripstart*(stripend+((whitespace+newline)^1/" ")+1)^0 )
local striplinepatterns={
["prune"]=p_prune_normal,
["prune and collapse"]=p_prune_collapse,
@@ -709,6 +710,7 @@ local striplinepatterns={
["retain"]=p_retain_normal,
["retain and collapse"]=p_retain_collapse,
["retain and no empty"]=p_retain_noempty,
+ ["collapse all"]=p_collapse_all,
["collapse"]=patterns.collapser,
}
setmetatable(striplinepatterns,{ __index=function(t,k) return p_prune_collapse end })
@@ -2090,7 +2092,7 @@ else
local v=t[0]
if v then
m=m+1
- r[m]="[0]='"
+ r[m]="[0]="
if type(v)=="table" then
fastserialize(v)
else
@@ -2879,7 +2881,9 @@ function parsers.groupedsplitat(symbol,withaction)
if not pattern then
local symbols=S(symbol)
local separator=space^0*symbols*space^0
- local value=lbrace*C((nobrace+nestedbraces)^0)*rbrace+C((nestedbraces+(1-(space^0*(symbols+P(-1)))))^0)
+ local value=lbrace*C((nobrace+nestedbraces)^0)
+*(rbrace*(#symbols+P(-1)))
++C((nestedbraces+(1-(space^0*(symbols+P(-1)))))^0)
if withaction then
local withvalue=Carg(1)*value/function(f,s) return f(s) end
pattern=spaces*withvalue*(separator*withvalue)^0
@@ -2965,7 +2969,17 @@ hashes.settings_to_set=table.setmetatableindex(function(t,k)
t[k]=v
return v
end)
-getmetatable(hashes.settings_to_set).__mode="kv"
+function parsers.settings_to_set(str)
+ return str and lpegmatch(pattern,str) or {}
+end
+local pattern=Ct((C((1-S(", "))^1)*S(", ")^0)^1)
+hashes.settings_to_list=table.setmetatableindex(function(t,k)
+ local v=k and lpegmatch(pattern,k) or {}
+ t[k]=v
+ return v
+end)
+getmetatable(hashes.settings_to_set ).__mode="kv"
+getmetatable(hashes.settings_to_list).__mode="kv"
function parsers.simple_hash_to_string(h,separator)
local t={}
local tn=0
@@ -3298,6 +3312,8 @@ local dimenfactors=allocate {
["pc"]=(1/12)/65536,
["dd"]=(1157/1238)/65536,
["cc"]=(1157/14856)/65536,
+ ["es"]=(9176/129)/65536,
+ ["ts"]=(4588/645)/65536,
}
local f_none=formatters["%s%s"]
local f_true=formatters["%0.5F%s"]
@@ -3323,12 +3339,13 @@ function number.topoints (n,fmt) return numbertodimen(n,"pt",fmt) end
function number.toinches (n,fmt) return numbertodimen(n,"in",fmt) end
function number.tocentimeters (n,fmt) return numbertodimen(n,"cm",fmt) end
function number.tomillimeters (n,fmt) return numbertodimen(n,"mm",fmt) end
-function number.toscaledpoints(n,fmt) return numbertodimen(n,"sp",fmt) end
function number.toscaledpoints(n) return n.."sp" end
function number.tobasepoints (n,fmt) return numbertodimen(n,"bp",fmt) end
function number.topicas (n,fmt) return numbertodimen(n "pc",fmt) end
function number.todidots (n,fmt) return numbertodimen(n,"dd",fmt) end
function number.tociceros (n,fmt) return numbertodimen(n,"cc",fmt) end
+function number.toediths (n,fmt) return numbertodimen(n,"es",fmt) end
+function number.totoves (n,fmt) return numbertodimen(n,"ts",fmt) end
local amount=(S("+-")^0*R("09")^0*P(".")^0*R("09")^0)+Cc("0")
local unit=R("az")^1+P("%")
local dimenpair=amount/tonumber*(unit^1/dimenfactors+Cc(1))
@@ -3342,7 +3359,7 @@ setmetatableindex(dimenfactors,function(t,s)
end)
local stringtodimen
local amount=S("+-")^0*R("09")^0*S(".,")^0*R("09")^0
-local unit=P("pt")+P("cm")+P("mm")+P("sp")+P("bp")+P("in")+P("pc")+P("dd")+P("cc")+P("nd")+P("nc")
+local unit=P("pt")+P("cm")+P("mm")+P("sp")+P("bp")+P("es")+P("ts")+P("pc")+P("dd")+P("cc")+P("in")
local validdimen=amount*unit
lpeg.patterns.validdimen=validdimen
local dimensions={}
@@ -3392,8 +3409,9 @@ function dimensions.__index(tab,key)
end
return 1/d
end
- dimenfactors["ex"]=4*1/65536
- dimenfactors["em"]=10*1/65536
+ dimenfactors["ex"]=4/65536
+ dimenfactors["em"]=10/65536
+ dimenfactors["eu"]=(9176/129)/65536
local known={} setmetatable(known,{ __mode="v" })
function dimen(a)
if a then
@@ -4984,11 +5002,13 @@ end
local files=utilities.files
local openfile=files.open
local closefile=files.close
+local getsize=files.size
local readstring=files.readstring
local readcardinal2=files.readcardinal2le
local readcardinal4=files.readcardinal4le
local setposition=files.setposition
local getposition=files.getposition
+local skipbytes=files.skip
local band=bit32.band
local rshift=bit32.rshift
local lshift=bit32.lshift
@@ -5011,6 +5031,55 @@ local openzipfile,closezipfile,unzipfile,foundzipfile,getziphash,getziplist do
handle=openfile(name,0),
}
end
+ local function update(handle,data)
+ position=data.offset
+ setposition(handle,position)
+ local signature=readstring(handle,4)
+ if signature=="PK\3\4" then
+ local version=readcardinal2(handle)
+ local flag=readcardinal2(handle)
+ local method=readcardinal2(handle)
+ skipbytes(handle,4)
+ local crc32=readcardinal4(handle)
+ local compressed=readcardinal4(handle)
+ local uncompressed=readcardinal4(handle)
+ local namelength=readcardinal2(handle)
+ local extralength=readcardinal2(handle)
+ local filename=readstring(handle,namelength)
+ local descriptor=band(flag,8)~=0
+ local encrypted=band(flag,1)~=0
+ local acceptable=method==0 or method==8
+ local skipped=0
+ local size=0
+ if encrypted then
+ size=readcardinal2(handle)
+ skipbytes(handle,size)
+ skipped=skipped+size+2
+ skipbytes(8)
+ skipped=skipped+8
+ size=readcardinal2(handle)
+ skipbytes(handle,size)
+ skipped=skipped+size+2
+ size=readcardinal4(handle)
+ skipbytes(handle,size)
+ skipped=skipped+size+4
+ size=readcardinal2(handle)
+ skipbytes(handle,size)
+ skipped=skipped+size+2
+ end
+ if acceptable then
+ if filename~=data.filename then
+ else
+ position=position+30+namelength+extralength+skipped
+ data.position=position
+ return position
+ end
+ else
+ end
+ end
+ data.position=false
+ return false
+ end
local function collect(z)
if not z.list then
local list={}
@@ -5018,72 +5087,68 @@ local openzipfile,closezipfile,unzipfile,foundzipfile,getziphash,getziplist do
local position=0
local index=0
local handle=z.handle
- while true do
- setposition(handle,position)
- local signature=readstring(handle,4)
- if signature=="PK\3\4" then
- local version=readcardinal2(handle)
- local flag=readcardinal2(handle)
- local method=readcardinal2(handle)
- local filetime=readcardinal2(handle)
- local filedate=readcardinal2(handle)
- local crc32=readcardinal4(handle)
- local compressed=readcardinal4(handle)
- local uncompressed=readcardinal4(handle)
- local namelength=readcardinal2(handle)
- local extralength=readcardinal2(handle)
- local filename=readstring(handle,namelength)
- local descriptor=band(flag,8)~=0
- local encrypted=band(flag,1)~=0
- local acceptable=method==0 or method==8
- local skipped=0
- local size=0
- if encrypted then
- size=readcardinal2(handle)
- skipbytes(size)
- skipped=skipped+size+2
- skipbytes(8)
- skipped=skipped+8
- size=readcardinal2(handle)
- skipbytes(size)
- skipped=skipped+size+2
- size=readcardinal4(handle)
- skipbytes(size)
- skipped=skipped+size+4
- size=readcardinal2(handle)
- skipbytes(size)
- skipped=skipped+size+2
- end
- position=position+30+namelength+extralength+skipped
- if descriptor then
- setposition(handle,position+compressed)
- crc32=readcardinal4(handle)
- compressed=readcardinal4(handle)
- uncompressed=readcardinal4(handle)
- end
- if acceptable then
- index=index+1
- local data={
- filename=filename,
- index=index,
- position=position,
- method=method,
- compressed=compressed,
- uncompressed=uncompressed,
- crc32=crc32,
- encrypted=encrypted,
- }
- hash[filename]=data
- list[index]=data
- else
+ local size=getsize(handle)
+ for i=size-4,size-64*1024,-1 do
+ setposition(handle,i)
+ local enddirsignature=readcardinal4(handle)
+ if enddirsignature==0x06054B50 then
+ local thisdisknumber=readcardinal2(handle)
+ local centraldisknumber=readcardinal2(handle)
+ local thisnofentries=readcardinal2(handle)
+ local totalnofentries=readcardinal2(handle)
+ local centralsize=readcardinal4(handle)
+ local centraloffset=readcardinal4(handle)
+ local commentlength=readcardinal2(handle)
+ local comment=readstring(handle,length)
+ if size-i>=22 then
+ if thisdisknumber==centraldisknumber then
+ setposition(handle,centraloffset)
+ while true do
+ if readcardinal4(handle)==0x02014B50 then
+ skipbytes(handle,4)
+ local flag=readcardinal2(handle)
+ local method=readcardinal2(handle)
+ skipbytes(handle,4)
+ local crc32=readcardinal4(handle)
+ local compressed=readcardinal4(handle)
+ local uncompressed=readcardinal4(handle)
+ local namelength=readcardinal2(handle)
+ local extralength=readcardinal2(handle)
+ local commentlength=readcardinal2(handle)
+ skipbytes(handle,8)
+ local headeroffset=readcardinal4(handle)
+ local filename=readstring(handle,namelength)
+ skipbytes(handle,extralength+commentlength)
+ local descriptor=band(flag,8)~=0
+ local encrypted=band(flag,1)~=0
+ local acceptable=method==0 or method==8
+ if acceptable then
+ index=index+1
+ local data={
+ filename=filename,
+ index=index,
+ position=nil,
+ method=method,
+ compressed=compressed,
+ uncompressed=uncompressed,
+ crc32=crc32,
+ encrypted=encrypted,
+ offset=headeroffset,
+ }
+ hash[filename]=data
+ list[index]=data
+ end
+ else
+ break
+ end
+ end
+ end
+ break
end
- position=position+compressed
- else
- break
end
- z.list=list
- z.hash=hash
end
+ z.list=list
+ z.hash=hash
end
end
function getziplist(z)
@@ -5122,7 +5187,10 @@ local openzipfile,closezipfile,unzipfile,foundzipfile,getziphash,getziplist do
local handle=z.handle
local position=data.position
local compressed=data.compressed
- if compressed>0 then
+ if position==nil then
+ position=update(handle,data)
+ end
+ if position and compressed>0 then
setposition(handle,position)
local result=readstring(handle,compressed)
if data.method==8 then
@@ -5333,8 +5401,10 @@ if xzip then
closezip(zipf)
end
end
- local function unzipdir(zipname,path,verbose)
+ local function unzipdir(zipname,path,verbose,collect,validate)
if type(zipname)=="table" then
+ validate=zipname.validate
+ collect=zipname.collect
verbose=zipname.verbose
path=zipname.path
zipname=zipname.zipname
@@ -5355,34 +5425,47 @@ if xzip then
local done=0
local steps=verbose=="steps"
local time=steps and osclock()
+ if collect then
+ collect={}
+ else
+ collect=false
+ end
for i=1,count do
local l=list[i]
local n=l.filename
- local d=unzipfile(z,n)
- if d then
- local p=filejoin(path,n)
- if mkdirs(dirname(p)) then
- if steps then
- total=total+#d
- done=done+1
- if done>=step then
- done=0
- logwriter(format("%4i files of %4i done, %10i bytes, %0.3f seconds",i,count,total,osclock()-time))
+ if not validate or validate(n) then
+ local d=unzipfile(z,n)
+ if d then
+ local p=filejoin(path,n)
+ if mkdirs(dirname(p)) then
+ if steps then
+ total=total+#d
+ done=done+1
+ if done>=step then
+ done=0
+ logwriter(format("%4i files of %4i done, %10i bytes, %0.3f seconds",i,count,total,osclock()-time))
+ end
+ elseif verbose then
+ logwriter(n)
+ end
+ savedata(p,d)
+ if collect then
+ collect[#collect+1]=p
end
- elseif verbose then
- logwriter(n)
end
- savedata(p,d)
+ else
+ logwriter(format("problem with file %s",n))
end
else
- logwriter(format("problem with file %s",n))
end
end
if steps then
logwriter(format("%4i files of %4i done, %10i bytes, %0.3f seconds",count,count,total,osclock()-time))
end
closezipfile(z)
- return true
+ if collect then
+ return collect
+ end
else
closezipfile(z)
end
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended.lua
index f483fd96e2f..7e8ad6010bf 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-extended.lua
@@ -30,8 +30,8 @@ lualibs = lualibs or { }
local lualibs_extended_module = {
name = "lualibs-extended",
- version = "2.75", --TAGVERSION
- date = "2022-10-04", --TAGDATE
+ version = "2.76", --TAGVERSION
+ date = "2023-07-13", --TAGDATE
description = "ConTeXt Lua libraries -- extended collection.",
author = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
copyright = "PRAGMA ADE / ConTeXt Development Team",
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-file.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-file.lua
index 9f8fd654833..70f8188dc15 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-file.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-file.lua
@@ -741,8 +741,24 @@ end
-- not used in context but was in luatex once:
-local symlinkattributes = lfs.symlinkattributes
+do
+
+ local symlinktarget = lfs.symlinktarget -- luametatex (always returns string)
+ local symlinkattributes = lfs.symlinkattributes -- luatex (can return nil)
+
+ if symlinktarget then
+ function lfs.readlink(name)
+ local target = symlinktarget(name)
+ return name ~= target and name or nil
+ end
+ elseif symlinkattributes then
+ function lfs.readlink(name)
+ return symlinkattributes(name,"target") or nil
+ end
+ else
+ function lfs.readlink(name)
+ return nil
+ end
+ end
-function lfs.readlink(name)
- return symlinkattributes(name,"target") or nil
end
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-string.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-string.lua
index 1dee85e2894..476820a175b 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-string.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-string.lua
@@ -7,7 +7,7 @@ if not modules then modules = { } end modules ['l-string'] = {
}
local string = string
-local sub, gmatch, format, char, byte, rep, lower = string.sub, string.gmatch, string.format, string.char, string.byte, string.rep, string.lower
+local sub, gmatch, format, char, byte, rep, lower, find = string.sub, string.gmatch, string.format, string.char, string.byte, string.rep, string.lower, string.find
local lpegmatch, patterns = lpeg.match, lpeg.patterns
local P, S, C, Ct, Cc, Cs = lpeg.P, lpeg.S, lpeg.C, lpeg.Ct, lpeg.Cc, lpeg.Cs
@@ -52,10 +52,26 @@ function string.quoted(str)
return format("%q",str) -- always double quote
end
-function string.count(str,pattern) -- variant 3
+-- function string.count(str,pattern) -- variant 3
+-- local n = 0
+-- for _ in gmatch(str,pattern) do -- not for utf
+-- n = n + 1
+-- end
+-- return n
+-- end
+
+function string.count(str,pattern)
local n = 0
- for _ in gmatch(str,pattern) do -- not for utf
- n = n + 1
+ local i = 1
+ local l = #pattern
+ while true do
+ i = find(str,pattern,i)
+ if i then
+ n = n + 1
+ i = i + l
+ else
+ break
+ end
end
return n
end
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-unicode.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-unicode.lua
index 5d9a7149bda..f98686c6b6d 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-unicode.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-unicode.lua
@@ -32,7 +32,6 @@ if not modules then modules = { } end modules ['l-unicode'] = {
-- dump, find, format, gfind, gmatch, gsub, lower, match, rep, reverse, upper
utf = utf or { }
--- unicode = nil
if not string.utfcharacters then
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-dim.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-dim.lua
index bb9eca96688..6462f3e4920 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-dim.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-dim.lua
@@ -6,14 +6,10 @@ if not modules then modules = { } end modules ['util-dim'] = {
license = "see context related readme files"
}
---[[ldx--
-<p>Internally <l n='luatex'/> work with scaled point, which are
-represented by integers. However, in practice, at east at the
-<l n='tex'/> end we work with more generic units like points (pt). Going
-from scaled points (numbers) to one of those units can be
-done by using the conversion factors collected in the following
-table.</p>
---ldx]]--
+-- Internally LuaTeX work with scaled point, which are represented by integers.
+-- However, in practice, at east at the TeX end we work with more generic units like
+-- points (pt). Going from scaled points (numbers) to one of those units can be done
+-- by using the conversion factors collected in the following table.
local format, match, gsub, type, setmetatable = string.format, string.match, string.gsub, type, setmetatable
local P, S, R, Cc, C, lpegmatch = lpeg.P, lpeg.S, lpeg.R, lpeg.Cc, lpeg.C, lpeg.match
@@ -45,7 +41,9 @@ local dimenfactors = allocate {
["dd"] = ( 1157/ 1238)/65536,
["cc"] = ( 1157/14856)/65536,
-- ["nd"] = (20320/21681)/65536,
- -- ["nc"] = ( 5080/65043)/65536
+ -- ["nc"] = ( 5080/65043)/65536,
+ ["es"] = ( 9176/ 129)/65536,
+ ["ts"] = ( 4588/ 645)/65536,
}
-- print(table.serialize(dimenfactors))
@@ -86,10 +84,8 @@ local dimenfactors = allocate {
-- ["sp"]=1,
-- }
---[[ldx--
-<p>A conversion function that takes a number, unit (string) and optional
-format (string) is implemented using this table.</p>
---ldx]]--
+-- A conversion function that takes a number, unit (string) and optional format
+-- (string) is implemented using this table.
local f_none = formatters["%s%s"]
local f_true = formatters["%0.5F%s"]
@@ -110,9 +106,7 @@ local function numbertodimen(n,unit,fmt) -- will be redefined later !
end
end
---[[ldx--
-<p>We collect a bunch of converters in the <type>number</type> namespace.</p>
---ldx]]--
+-- We collect a bunch of converters in the 'number' namespace.
number.maxdimen = 1073741823
number.todimen = numbertodimen
@@ -122,7 +116,7 @@ function number.topoints (n,fmt) return numbertodimen(n,"pt",fmt) end
function number.toinches (n,fmt) return numbertodimen(n,"in",fmt) end
function number.tocentimeters (n,fmt) return numbertodimen(n,"cm",fmt) end
function number.tomillimeters (n,fmt) return numbertodimen(n,"mm",fmt) end
-function number.toscaledpoints(n,fmt) return numbertodimen(n,"sp",fmt) end
+-------- number.toscaledpoints(n,fmt) return numbertodimen(n,"sp",fmt) end
function number.toscaledpoints(n) return n .. "sp" end
function number.tobasepoints (n,fmt) return numbertodimen(n,"bp",fmt) end
function number.topicas (n,fmt) return numbertodimen(n "pc",fmt) end
@@ -130,14 +124,13 @@ function number.todidots (n,fmt) return numbertodimen(n,"dd",fmt) end
function number.tociceros (n,fmt) return numbertodimen(n,"cc",fmt) end
-------- number.tonewdidots (n,fmt) return numbertodimen(n,"nd",fmt) end
-------- number.tonewciceros (n,fmt) return numbertodimen(n,"nc",fmt) end
+function number.toediths (n,fmt) return numbertodimen(n,"es",fmt) end
+function number.totoves (n,fmt) return numbertodimen(n,"ts",fmt) end
---[[ldx--
-<p>More interesting it to implement a (sort of) dimen datatype, one
-that permits calculations too. First we define a function that
-converts a string to scaledpoints. We use <l n='lpeg'/>. We capture
-a number and optionally a unit. When no unit is given a constant
-capture takes place.</p>
---ldx]]--
+-- More interesting it to implement a (sort of) dimen datatype, one that permits
+-- calculations too. First we define a function that converts a string to
+-- scaledpoints. We use LPEG. We capture a number and optionally a unit. When no
+-- unit is given a constant capture takes place.
local amount = (S("+-")^0 * R("09")^0 * P(".")^0 * R("09")^0) + Cc("0")
local unit = R("az")^1 + P("%")
@@ -152,21 +145,16 @@ function number.splitdimen(str)
return lpegmatch(splitter,str)
end
---[[ldx--
-<p>We use a metatable to intercept errors. When no key is found in
-the table with factors, the metatable will be consulted for an
-alternative index function.</p>
---ldx]]--
+-- We use a metatable to intercept errors. When no key is found in the table with
+-- factors, the metatable will be consulted for an alternative index function.
setmetatableindex(dimenfactors, function(t,s)
-- error("wrong dimension: " .. (s or "?")) -- better a message
return false
end)
---[[ldx--
-<p>We redefine the following function later on, so we comment it
-here (which saves us bytecodes.</p>
---ldx]]--
+-- We redefine the following function later on, so we comment it here (which saves
+-- us bytecodes.
-- function string.todimen(str)
-- if type(str) == "number" then
@@ -182,44 +170,38 @@ here (which saves us bytecodes.</p>
local stringtodimen -- assigned later (commenting saves bytecode)
local amount = S("+-")^0 * R("09")^0 * S(".,")^0 * R("09")^0
-local unit = P("pt") + P("cm") + P("mm") + P("sp") + P("bp") + P("in") +
- P("pc") + P("dd") + P("cc") + P("nd") + P("nc")
+local unit = P("pt") + P("cm") + P("mm") + P("sp") + P("bp")
+ + P("es") + P("ts") + P("pc") + P("dd") + P("cc")
+ + P("in")
+ -- + P("nd") + P("nc")
local validdimen = amount * unit
lpeg.patterns.validdimen = validdimen
---[[ldx--
-<p>This converter accepts calls like:</p>
-
-<typing>
-string.todimen("10")
-string.todimen(".10")
-string.todimen("10.0")
-string.todimen("10.0pt")
-string.todimen("10pt")
-string.todimen("10.0pt")
-</typing>
-
-<p>With this in place, we can now implement a proper datatype for dimensions, one
-that permits us to do this:</p>
-
-<typing>
-s = dimen "10pt" + dimen "20pt" + dimen "200pt"
- - dimen "100sp" / 10 + "20pt" + "0pt"
-</typing>
-
-<p>We create a local metatable for this new type:</p>
---ldx]]--
+-- This converter accepts calls like:
+--
+-- string.todimen("10")
+-- string.todimen(".10")
+-- string.todimen("10.0")
+-- string.todimen("10.0pt")
+-- string.todimen("10pt")
+-- string.todimen("10.0pt")
+--
+-- With this in place, we can now implement a proper datatype for dimensions, one
+-- that permits us to do this:
+--
+-- s = dimen "10pt" + dimen "20pt" + dimen "200pt"
+-- - dimen "100sp" / 10 + "20pt" + "0pt"
+--
+-- We create a local metatable for this new type:
local dimensions = { }
---[[ldx--
-<p>The main (and globally) visible representation of a dimen is defined next: it is
-a one-element table. The unit that is returned from the match is normally a number
-(one of the previously defined factors) but we also accept functions. Later we will
-see why. This function is redefined later.</p>
---ldx]]--
+-- The main (and globally) visible representation of a dimen is defined next: it is
+-- a one-element table. The unit that is returned from the match is normally a
+-- number (one of the previously defined factors) but we also accept functions.
+-- Later we will see why. This function is redefined later.
-- function dimen(a)
-- if a then
@@ -241,11 +223,9 @@ see why. This function is redefined later.</p>
-- end
-- end
---[[ldx--
-<p>This function return a small hash with a metatable attached. It is
-through this metatable that we can do the calculations. We could have
-shared some of the code but for reasons of speed we don't.</p>
---ldx]]--
+-- This function return a small hash with a metatable attached. It is through this
+-- metatable that we can do the calculations. We could have shared some of the code
+-- but for reasons of speed we don't.
function dimensions.__add(a, b)
local ta, tb = type(a), type(b)
@@ -281,20 +261,16 @@ function dimensions.__unm(a)
return setmetatable({ - a }, dimensions)
end
---[[ldx--
-<p>It makes no sense to implement the power and modulo function but
-the next two do make sense because they permits is code like:</p>
-
-<typing>
-local a, b = dimen "10pt", dimen "11pt"
-...
-if a > b then
- ...
-end
-</typing>
---ldx]]--
-
--- makes no sense: dimensions.__pow and dimensions.__mod
+-- It makes no sense to implement the power and modulo function but
+-- the next two do make sense because they permits is code like:
+--
+-- local a, b = dimen "10pt", dimen "11pt"
+-- ...
+-- if a > b then
+-- ...
+-- end
+--
+-- This also makes no sense: dimensions.__pow and dimensions.__mod.
function dimensions.__lt(a, b)
return a[1] < b[1]
@@ -304,24 +280,17 @@ function dimensions.__eq(a, b)
return a[1] == b[1]
end
---[[ldx--
-<p>We also need to provide a function for conversion to string (so that
-we can print dimensions). We print them as points, just like <l n='tex'/>.</p>
---ldx]]--
+-- We also need to provide a function for conversion to string (so that we can print
+-- dimensions). We print them as points, just like TeX.
function dimensions.__tostring(a)
return a[1]/65536 .. "pt" -- instead of todimen(a[1])
end
---[[ldx--
-<p>Since it does not take much code, we also provide a way to access
-a few accessors</p>
-
-<typing>
-print(dimen().pt)
-print(dimen().sp)
-</typing>
---ldx]]--
+-- Since it does not take much code, we also provide a way to access a few accessors
+--
+-- print(dimen().pt)
+-- print(dimen().sp)
function dimensions.__index(tab,key)
local d = dimenfactors[key]
@@ -332,41 +301,34 @@ function dimensions.__index(tab,key)
return 1/d
end
---[[ldx--
-<p>In the converter from string to dimension we support functions as
-factors. This is because in <l n='tex'/> we have a few more units:
-<type>ex</type> and <type>em</type>. These are not constant factors but
-depend on the current font. They are not defined by default, but need
-an explicit function call. This is because at the moment that this code
-is loaded, the relevant tables that hold the functions needed may not
-yet be available.</p>
---ldx]]--
-
- dimenfactors["ex"] = 4 * 1/65536 -- 4pt
- dimenfactors["em"] = 10 * 1/65536 -- 10pt
--- dimenfactors["%"] = 4 * 1/65536 -- 400pt/100
-
---[[ldx--
-<p>The previous code is rather efficient (also thanks to <l n='lpeg'/>) but we
-can speed it up by caching converted dimensions. On my machine (2008) the following
-loop takes about 25.5 seconds.</p>
-
-<typing>
-for i=1,1000000 do
- local s = dimen "10pt" + dimen "20pt" + dimen "200pt"
- - dimen "100sp" / 10 + "20pt" + "0pt"
-end
-</typing>
-
-<p>When we cache converted strings this becomes 16.3 seconds. In order not
-to waste too much memory on it, we tag the values of the cache as being
-week which mean that the garbage collector will collect them in a next
-sweep. This means that in most cases the speed up is mostly affecting the
-current couple of calculations and as such the speed penalty is small.</p>
-
-<p>We redefine two previous defined functions that can benefit from
-this:</p>
---ldx]]--
+-- In the converter from string to dimension we support functions as factors. This
+-- is because in TeX we have a few more units: 'ex' and 'em'. These are not constant
+-- factors but depend on the current font. They are not defined by default, but need
+-- an explicit function call. This is because at the moment that this code is
+-- loaded, the relevant tables that hold the functions needed may not yet be
+-- available.
+
+ dimenfactors["ex"] = 4 /65536 -- 4pt
+ dimenfactors["em"] = 10 /65536 -- 10pt
+-- dimenfactors["%"] = 4 /65536 -- 400pt/100
+ dimenfactors["eu"] = (9176/129)/65536 -- 1es
+
+-- The previous code is rather efficient (also thanks to LPEG) but we can speed it
+-- up by caching converted dimensions. On my machine (2008) the following loop takes
+-- about 25.5 seconds.
+--
+-- for i=1,1000000 do
+-- local s = dimen "10pt" + dimen "20pt" + dimen "200pt"
+-- - dimen "100sp" / 10 + "20pt" + "0pt"
+-- end
+--
+-- When we cache converted strings this becomes 16.3 seconds. In order not to waste
+-- too much memory on it, we tag the values of the cache as being week which mean
+-- that the garbage collector will collect them in a next sweep. This means that in
+-- most cases the speed up is mostly affecting the current couple of calculations
+-- and as such the speed penalty is small.
+--
+-- We redefine two previous defined functions that can benefit from this:
local known = { } setmetatable(known, { __mode = "v" })
@@ -436,14 +398,10 @@ function number.toscaled(d)
return format("%0.5f",d/0x10000) -- 2^16
end
---[[ldx--
-<p>In a similar fashion we can define a glue datatype. In that case we
-probably use a hash instead of a one-element table.</p>
---ldx]]--
-
---[[ldx--
-<p>Goodie:s</p>
---ldx]]--
+-- In a similar fashion we can define a glue datatype. In that case we probably use
+-- a hash instead of a one-element table.
+--
+-- A goodie:
function number.percent(n,d) -- will be cleaned up once luatex 0.30 is out
d = d or texget("hsize")
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-prs.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-prs.lua
index 635b610e072..a527555db7e 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-prs.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-prs.lua
@@ -264,8 +264,13 @@ function parsers.groupedsplitat(symbol,withaction)
if not pattern then
local symbols = S(symbol)
local separator = space^0 * symbols * space^0
- local value = lbrace * C((nobrace + nestedbraces)^0) * rbrace
- + C((nestedbraces + (1-(space^0*(symbols+P(-1)))))^0)
+ local value =
+ lbrace
+ * C((nobrace + nestedbraces)^0)
+ -- * rbrace
+ * (rbrace * (#symbols + P(-1))) -- new per 2023-03-11
+ +
+ C((nestedbraces + (1-(space^0*(symbols+P(-1)))))^0)
if withaction then
local withvalue = Carg(1) * value / function(f,s) return f(s) end
pattern = spaces * withvalue * (separator*withvalue)^0
@@ -378,9 +383,25 @@ hashes.settings_to_set = table.setmetatableindex(function(t,k) -- experiment, n
return v
end)
+function parsers.settings_to_set(str)
+ return str and lpegmatch(pattern,str) or { }
+end
+
+local pattern = Ct((C((1-S(", "))^1) * S(", ")^0)^1)
+
+hashes.settings_to_list = table.setmetatableindex(function(t,k) -- experiment, not public
+ local v = k and lpegmatch(pattern,k) or { }
+ t[k] = v
+ return v
+end)
+
+-- inspect(hashes.settings_to_set["a,b, c, d"])
+-- inspect(hashes.settings_to_list["a,b, c, d"])
+
-- as we use a next, we are not sure when the gc kicks in
-getmetatable(hashes.settings_to_set).__mode = "kv" -- could be an option (maybe sharing makes sense)
+getmetatable(hashes.settings_to_set ).__mode = "kv" -- could be an option (maybe sharing makes sense)
+getmetatable(hashes.settings_to_list).__mode = "kv" -- could be an option (maybe sharing makes sense)
function parsers.simple_hash_to_string(h, separator)
local t = { }
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-sac.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-sac.lua
index 36daef81673..9d2e8356da3 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-sac.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-sac.lua
@@ -551,14 +551,14 @@ if bit32 and not streams.tocardinal1 then
local char = string.char
streams.tocardinal1 = char
- function streams.tocardinal2(n) return char(extract( 8,8),extract( 0,8)) end
- function streams.tocardinal3(n) return char(extract(16,8),extract( 8,8),extract(0,8)) end
- function streams.tocardinal4(n) return char(extract(24,8),extract(16,8),extract(8,8),extract(0,8)) end
+ function streams.tocardinal2(n) return char(extract(n, 8,8),extract(n, 0,8)) end
+ function streams.tocardinal3(n) return char(extract(n,16,8),extract(n, 8,8),extract(n,0,8)) end
+ function streams.tocardinal4(n) return char(extract(n,24,8),extract(n,16,8),extract(n,8,8),extract(n,0,8)) end
streams.tocardinal1le = char
- function streams.tocardinal2le(n) return char(extract(0,8),extract(8,8)) end
- function streams.tocardinal3le(n) return char(extract(0,8),extract(8,8),extract(16,8)) end
- function streams.tocardinal4le(n) return char(extract(0,8),extract(8,8),extract(16,8),extract(24,8)) end
+ function streams.tocardinal2le(n) return char(extract(n,0,8),extract(n,8,8)) end
+ function streams.tocardinal3le(n) return char(extract(n,0,8),extract(n,8,8),extract(n,16,8)) end
+ function streams.tocardinal4le(n) return char(extract(n,0,8),extract(n,8,8),extract(n,16,8),extract(n,24,8)) end
end
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-str.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-str.lua
index b5c721a41d2..a9150b886ac 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-str.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-str.lua
@@ -269,6 +269,7 @@ local p_prune_intospace = Cs ( noleading * ( notrailing + intospace + 1
local p_retain_normal = Cs ( ( normalline + normalempty )^0 )
local p_retain_collapse = Cs ( ( normalline + doubleempty )^0 )
local p_retain_noempty = Cs ( ( normalline + singleempty )^0 )
+local p_collapse_all = Cs ( stripstart * ( stripend + ((whitespace+newline)^1/" ") + 1)^0 )
-- function striplines(str,prune,collapse,noempty)
-- if prune then
@@ -298,6 +299,7 @@ local striplinepatterns = {
["retain"] = p_retain_normal,
["retain and collapse"] = p_retain_collapse,
["retain and no empty"] = p_retain_noempty,
+ ["collapse all"] = p_collapse_all,
["collapse"] = patterns.collapser,
}
@@ -313,6 +315,9 @@ function strings.collapse(str) -- maybe also in strings
return str and lpegmatch(p_prune_intospace,str) or str
end
+-- local s = "\naa\n\naa\na a\n\n"
+-- print("["..strings.striplines(s,"collapse all").."]")
+
-- also see: string.collapsespaces
strings.striplong = strings.striplines -- for old times sake
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-tab.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-tab.lua
index 64fa1af4fb3..58ca3bcb10e 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-tab.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-tab.lua
@@ -432,7 +432,7 @@ else
local v = t[0]
if v then
m = m + 1
- r[m] = "[0]='"
+ r[m] = "[0]="
if type(v) == "table" then
fastserialize(v)
else
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-zip.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-zip.lua
index bd8fdf287f9..194eb56972f 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-zip.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs-util-zip.lua
@@ -34,11 +34,13 @@ end
local files = utilities.files
local openfile = files.open
local closefile = files.close
+local getsize = files.size
local readstring = files.readstring
local readcardinal2 = files.readcardinal2le
local readcardinal4 = files.readcardinal4le
local setposition = files.setposition
local getposition = files.getposition
+local skipbytes = files.skip
local band = bit32.band
local rshift = bit32.rshift
@@ -69,6 +71,158 @@ local openzipfile, closezipfile, unzipfile, foundzipfile, getziphash, getziplist
}
end
+ -- https://pkware.cachefly.net/webdocs/casestudies/APPNOTE.TXT
+
+-- local function collect(z)
+-- if not z.list then
+-- local list = { }
+-- local hash = { }
+-- local position = 0
+-- local index = 0
+-- local handle = z.handle
+-- while true do
+-- setposition(handle,position)
+-- local signature = readstring(handle,4)
+-- if signature == "PK\3\4" then
+-- -- [local file header 1]
+-- -- [encryption header 1]
+-- -- [file data 1]
+-- -- [data descriptor 1]
+-- local version = readcardinal2(handle)
+-- local flag = readcardinal2(handle)
+-- local method = readcardinal2(handle)
+-- local filetime = readcardinal2(handle)
+-- local filedate = readcardinal2(handle)
+-- local crc32 = readcardinal4(handle)
+-- local compressed = readcardinal4(handle)
+-- local uncompressed = readcardinal4(handle)
+-- local namelength = readcardinal2(handle)
+-- local extralength = readcardinal2(handle)
+-- local filename = readstring(handle,namelength)
+-- local descriptor = band(flag,8) ~= 0
+-- local encrypted = band(flag,1) ~= 0
+-- local acceptable = method == 0 or method == 8
+-- -- 30 bytes of header including the signature
+-- local skipped = 0
+-- local size = 0
+-- if encrypted then
+-- size = readcardinal2(handle)
+-- skipbytes(handle,size)
+-- skipped = skipped + size + 2
+-- skipbytes(8)
+-- skipped = skipped + 8
+-- size = readcardinal2(handle)
+-- skipbytes(handle,size)
+-- skipped = skipped + size + 2
+-- size = readcardinal4(handle)
+-- skipbytes(handle,size)
+-- skipped = skipped + size + 4
+-- size = readcardinal2(handle)
+-- skipbytes(handle,size)
+-- skipped = skipped + size + 2
+-- end
+-- position = position + 30 + namelength + extralength + skipped
+-- -- if descriptor then
+-- -- -- where is this one located
+-- -- setposition(handle,position + compressed)
+-- -- crc32 = readcardinal4(handle)
+-- -- compressed = readcardinal4(handle)
+-- -- uncompressed = readcardinal4(handle)
+-- -- end
+-- if acceptable then
+-- index = index + 1
+-- local data = {
+-- filename = filename,
+-- index = index,
+-- position = position,
+-- method = method,
+-- compressed = compressed,
+-- uncompressed = uncompressed,
+-- crc32 = crc32,
+-- encrypted = encrypted,
+-- }
+-- hash[filename] = data
+-- list[index] = data
+-- else
+-- -- maybe a warning when encrypted
+-- end
+-- position = position + compressed
+-- else
+-- break
+-- end
+-- z.list = list
+-- z.hash = hash
+-- end
+-- end
+-- end
+-- end
+
+-- end
+-- end
+
+ local function update(handle,data)
+ position = data.offset
+ setposition(handle,position)
+ local signature = readstring(handle,4)
+ if signature == "PK\3\4" then -- 0x04034B50
+ -- [local file header 1]
+ -- [encryption header 1]
+ -- [file data 1]
+ -- [data descriptor 1]
+ local version = readcardinal2(handle)
+ local flag = readcardinal2(handle)
+ local method = readcardinal2(handle)
+ skipbytes(handle,4)
+ ----- filetime = readcardinal2(handle)
+ ----- filedate = readcardinal2(handle)
+ local crc32 = readcardinal4(handle)
+ local compressed = readcardinal4(handle)
+ local uncompressed = readcardinal4(handle)
+ local namelength = readcardinal2(handle)
+ local extralength = readcardinal2(handle)
+ local filename = readstring(handle,namelength)
+ local descriptor = band(flag,8) ~= 0
+ local encrypted = band(flag,1) ~= 0
+ local acceptable = method == 0 or method == 8
+ -- 30 bytes of header including the signature
+ local skipped = 0
+ local size = 0
+ if encrypted then
+ size = readcardinal2(handle)
+ skipbytes(handle,size)
+ skipped = skipped + size + 2
+ skipbytes(8)
+ skipped = skipped + 8
+ size = readcardinal2(handle)
+ skipbytes(handle,size)
+ skipped = skipped + size + 2
+ size = readcardinal4(handle)
+ skipbytes(handle,size)
+ skipped = skipped + size + 4
+ size = readcardinal2(handle)
+ skipbytes(handle,size)
+ skipped = skipped + size + 2
+ end
+ if acceptable then
+ if filename ~= data.filename then
+ -- elseif method ~= data.method then
+ -- elseif encrypted ~= data.encrypted then
+ -- elseif crc32 ~= 0 and crc32 ~= data.crc32 then
+ -- elseif uncompressed ~= 0 and uncompressed ~= data.uncompressed then
+ -- elseif compressed ~= 0 and compressed ~= data.compressed then
+ else
+ position = position + 30 + namelength + extralength + skipped
+ data.position = position
+ return position
+ end
+ else
+ -- maybe a warning when encrypted
+ end
+ end
+ data.position = false
+ return false
+ end
+
local function collect(z)
if not z.list then
local list = { }
@@ -76,78 +230,88 @@ local openzipfile, closezipfile, unzipfile, foundzipfile, getziphash, getziplist
local position = 0
local index = 0
local handle = z.handle
- while true do
- setposition(handle,position)
- local signature = readstring(handle,4)
- if signature == "PK\3\4" then
- -- [local file header 1]
- -- [encryption header 1]
- -- [file data 1]
- -- [data descriptor 1]
- local version = readcardinal2(handle)
- local flag = readcardinal2(handle)
- local method = readcardinal2(handle)
- local filetime = readcardinal2(handle)
- local filedate = readcardinal2(handle)
- local crc32 = readcardinal4(handle)
- local compressed = readcardinal4(handle)
- local uncompressed = readcardinal4(handle)
- local namelength = readcardinal2(handle)
- local extralength = readcardinal2(handle)
- local filename = readstring(handle,namelength)
- local descriptor = band(flag,8) ~= 0
- local encrypted = band(flag,1) ~= 0
- local acceptable = method == 0 or method == 8
- -- 30 bytes of header including the signature
- local skipped = 0
- local size = 0
- if encrypted then
- size = readcardinal2(handle)
- skipbytes(size)
- skipped = skipped + size + 2
- skipbytes(8)
- skipped = skipped + 8
- size = readcardinal2(handle)
- skipbytes(size)
- skipped = skipped + size + 2
- size = readcardinal4(handle)
- skipbytes(size)
- skipped = skipped + size + 4
- size = readcardinal2(handle)
- skipbytes(size)
- skipped = skipped + size + 2
- end
- position = position + 30 + namelength + extralength + skipped
- if descriptor then
- setposition(handle,position + compressed)
- crc32 = readcardinal4(handle)
- compressed = readcardinal4(handle)
- uncompressed = readcardinal4(handle)
- end
- if acceptable then
- index = index + 1
- local data = {
- filename = filename,
- index = index,
- position = position,
- method = method,
- compressed = compressed,
- uncompressed = uncompressed,
- crc32 = crc32,
- encrypted = encrypted,
- }
- hash[filename] = data
- list[index] = data
- else
- -- maybe a warning when encrypted
+ local size = getsize(handle)
+ --
+ -- Not all files have the compressed into set so we need to get the directory
+ -- first. We only handle single disk zip files.
+ --
+ for i=size-4,size-64*1024,-1 do
+ setposition(handle,i)
+ local enddirsignature = readcardinal4(handle)
+ if enddirsignature == 0x06054B50 then
+ local thisdisknumber = readcardinal2(handle)
+ local centraldisknumber = readcardinal2(handle)
+ local thisnofentries = readcardinal2(handle)
+ local totalnofentries = readcardinal2(handle)
+ local centralsize = readcardinal4(handle)
+ local centraloffset = readcardinal4(handle)
+ local commentlength = readcardinal2(handle)
+ local comment = readstring(handle,length)
+ if size - i >= 22 then
+ if thisdisknumber == centraldisknumber then
+ setposition(handle,centraloffset)
+ while true do
+ if readcardinal4(handle) == 0x02014B50 then
+ skipbytes(handle,4)
+ ----- versionmadeby = readcardinal2(handle)
+ ----- versionneeded = readcardinal2(handle)
+ local flag = readcardinal2(handle)
+ local method = readcardinal2(handle)
+ skipbytes(handle,4)
+ ----- filetime = readcardinal2(handle)
+ ----- filedate = readcardinal2(handle)
+ local crc32 = readcardinal4(handle)
+ local compressed = readcardinal4(handle)
+ local uncompressed = readcardinal4(handle)
+ local namelength = readcardinal2(handle)
+ local extralength = readcardinal2(handle)
+ local commentlength = readcardinal2(handle)
+ skipbytes(handle,8)
+ ----- disknumber = readcardinal2(handle)
+ ----- intattributes = readcardinal2(handle)
+ ----- extattributes = readcardinal4(handle)
+ local headeroffset = readcardinal4(handle)
+ local filename = readstring(handle,namelength)
+ skipbytes(handle,extralength+commentlength)
+ ----- extradata = readstring(handle,extralength)
+ ----- comment = readstring(handle,commentlength)
+ --
+ local descriptor = band(flag,8) ~= 0
+ local encrypted = band(flag,1) ~= 0
+ local acceptable = method == 0 or method == 8
+ if acceptable then
+ index = index + 1
+ local data = {
+ filename = filename,
+ index = index,
+ position = nil,
+ method = method,
+ compressed = compressed,
+ uncompressed = uncompressed,
+ crc32 = crc32,
+ encrypted = encrypted,
+ offset = headeroffset,
+ }
+ hash[filename] = data
+ list[index] = data
+ end
+ else
+ break
+ end
+ end
+ end
+ break
end
- position = position + compressed
- else
- break
end
- z.list = list
- z.hash = hash
end
+ -- for i=1,index do -- delayed
+ -- local data = list[i]
+ -- if not data.position then
+ -- update(handle,list[i])
+ -- end
+ -- end
+ z.list = list
+ z.hash = hash
end
end
@@ -156,6 +320,7 @@ local openzipfile, closezipfile, unzipfile, foundzipfile, getziphash, getziplist
if not list then
collect(z)
end
+ -- inspect(z.list)
return z.list
end
@@ -193,7 +358,10 @@ local openzipfile, closezipfile, unzipfile, foundzipfile, getziphash, getziplist
local handle = z.handle
local position = data.position
local compressed = data.compressed
- if compressed > 0 then
+ if position == nil then
+ position = update(handle,data)
+ end
+ if position and compressed > 0 then
setposition(handle,position)
local result = readstring(handle,compressed)
if data.method == 8 then
@@ -451,11 +619,13 @@ if xzip then -- flate then do
end
end
- local function unzipdir(zipname,path,verbose)
+ local function unzipdir(zipname,path,verbose,collect,validate)
if type(zipname) == "table" then
- verbose = zipname.verbose
- path = zipname.path
- zipname = zipname.zipname
+ validate = zipname.validate
+ collect = zipname.collect
+ verbose = zipname.verbose
+ path = zipname.path
+ zipname = zipname.zipname
end
if not zipname or zipname == "" then
return
@@ -473,34 +643,49 @@ if xzip then -- flate then do
local done = 0
local steps = verbose == "steps"
local time = steps and osclock()
+ -- local skip = 0
+ if collect then
+ collect = { }
+ else
+ collect = false
+ end
for i=1,count do
local l = list[i]
local n = l.filename
- local d = unzipfile(z,n) -- true for check
- if d then
- local p = filejoin(path,n)
- if mkdirs(dirname(p)) then
- if steps then
- total = total + #d
- done = done + 1
- if done >= step then
- done = 0
- logwriter(format("%4i files of %4i done, %10i bytes, %0.3f seconds",i,count,total,osclock()-time))
+ if not validate or validate(n) then
+ local d = unzipfile(z,n) -- true for check
+ if d then
+ local p = filejoin(path,n)
+ if mkdirs(dirname(p)) then
+ if steps then
+ total = total + #d
+ done = done + 1
+ if done >= step then
+ done = 0
+ logwriter(format("%4i files of %4i done, %10i bytes, %0.3f seconds",i,count,total,osclock()-time))
+ end
+ elseif verbose then
+ logwriter(n)
+ end
+ savedata(p,d)
+ if collect then
+ collect[#collect+1] = p
end
- elseif verbose then
- logwriter(n)
end
- savedata(p,d)
+ else
+ logwriter(format("problem with file %s",n))
end
else
- logwriter(format("problem with file %s",n))
+ -- skip = skip + 1
end
end
if steps then
logwriter(format("%4i files of %4i done, %10i bytes, %0.3f seconds",count,count,total,osclock()-time))
end
closezipfile(z)
- return true
+ if collect then
+ return collect
+ end
else
closezipfile(z)
end
diff --git a/Master/texmf-dist/tex/luatex/lualibs/lualibs.lua b/Master/texmf-dist/tex/luatex/lualibs/lualibs.lua
index 9681841d399..2fdf0058e14 100644
--- a/Master/texmf-dist/tex/luatex/lualibs/lualibs.lua
+++ b/Master/texmf-dist/tex/luatex/lualibs/lualibs.lua
@@ -25,8 +25,8 @@ lualibs = lualibs or { }
lualibs.module_info = {
name = "lualibs",
- version = "2.75", --TAGVERSION
- date = "2022-10-04", --TAGDATE
+ version = "2.76", --TAGVERSION
+ date = "2023-07-13", --TAGDATE
description = "ConTeXt Lua standard libraries.",
author = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
copyright = "PRAGMA ADE / ConTeXt Development Team",