[latex3-commits] [git/LaTeX3-latex3-lualibs] v2.72-20200831: imported context from 20200831 (1a15e0c)

Ulrike Fischer fischer at troubleshooting-tex.de
Mon Aug 31 23:20:29 CEST 2020


Repository : https://github.com/latex3/lualibs
On branch  : v2.72-20200831
Link       : https://github.com/latex3/lualibs/commit/1a15e0c67fe689cd3c600dc02b3bafc015e4f492

>---------------------------------------------------------------

commit 1a15e0c67fe689cd3c600dc02b3bafc015e4f492
Author: Ulrike Fischer <fischer at troubleshooting-tex.de>
Date:   Mon Aug 31 23:20:29 2020 +0200

    imported context from 20200831


>---------------------------------------------------------------

1a15e0c67fe689cd3c600dc02b3bafc015e4f492
 CTANREADME.md               |  6 +--
 NEWS                        |  3 ++
 README.md                   |  6 +--
 build.lua                   |  6 +--
 lualibs-basic-merged.lua    | 49 +++++++++++++++---------
 lualibs-extended-merged.lua | 90 +++++++++++++++++++++++----------------------
 lualibs-lpeg.lua            |  8 +++-
 lualibs-lua.lua             |  6 ---
 lualibs-os.lua              | 12 +++++-
 lualibs-package.lua         | 25 +++++++------
 lualibs-trac-inf.lua        | 41 +++++++++------------
 lualibs-unicode.lua         |  1 +
 lualibs-util-prs.lua        | 38 +++++++++++++------
 lualibs-util-str.lua        | 86 ++++++++++++++-----------------------------
 lualibs-util-tab.lua        |  9 +++++
 lualibs.dtx                 | 18 ++++-----
 16 files changed, 209 insertions(+), 195 deletions(-)

diff --git a/CTANREADME.md b/CTANREADME.md
index bbbf699..3519300 100644
--- a/CTANREADME.md
+++ b/CTANREADME.md
@@ -1,10 +1,10 @@
 # The Lualibs Package
 
-VERSION: 2.71
+VERSION: 2.72
 
-DATE: 2020-05-01
+DATE: 2020-08-31
 
-FONTLOADERDATE: 2020-04-30
+FONTLOADERDATE: 2020-08-31
 
 Lualibs is a collection of Lua modules useful for general programming.
 
diff --git a/NEWS b/NEWS
index 486b82b..af54318 100644
--- a/NEWS
+++ b/NEWS
@@ -1,4 +1,7 @@
                         History of the lualibs package
+2020/08/31 v2.72/
+    * sync with Context current as of 2020/08/31.
+
 2020/05/01 v2.71/
     * sync with Context current as of 2020/04/30.
                         
diff --git a/README.md b/README.md
index 6800662..5e075dc 100644
--- a/README.md
+++ b/README.md
@@ -1,7 +1,7 @@
 # The Lualibs Package
 
-![Version: 2.71](https://img.shields.io/badge/current_version-2.71-blue.svg?style=flat-square)
-![Date: 2020-05-01](https://img.shields.io/badge/date-2020--05--01-blue.svg?style=flat-square)
+![Version: 2.72](https://img.shields.io/badge/current_version-2.72-blue.svg?style=flat-square)
+![Date: 2020-08-31](https://img.shields.io/badge/date-2020--08--31-blue.svg?style=flat-square)
 [![License: GNU GPLv2](https://img.shields.io/badge/license-GNU_GPLv2-blue.svg?style=flat-square)](http://www.gnu.org/licenses/old-licenses/gpl-2.0.html)
 
 
@@ -15,7 +15,7 @@ This package has been developed by the LuaLaTeX development team on
 <http://github.com/lualatex/lualibs>. 
 
 The current version has been build by the LaTeX3 Project Team on
-<https://github.com/latex3/lualibs/> from context 2020-04-30. 
+<https://github.com/latex3/lualibs/> from context 2020-08-31. 
 
 Please see the documentation lualibs.pdf for more information.
 
diff --git a/build.lua b/build.lua
index aa96736..be0d9b5 100644
--- a/build.lua
+++ b/build.lua
@@ -1,7 +1,7 @@
 -- Build script for lualibs
-packageversion= "2.71"
-packagedate= "2020-05-01"
-fontloaderdate= "2020-04-30" -- only as record.
+packageversion= "2.72"
+packagedate= "2020-08-31"
+fontloaderdate= "2020-08-31" -- only as record.
 
 module   = "lualibs"
 ctanpkg  = "lualibs"
diff --git a/lualibs-basic-merged.lua b/lualibs-basic-merged.lua
index 24a62e3..147cc33 100644
--- a/lualibs-basic-merged.lua
+++ b/lualibs-basic-merged.lua
@@ -1,6 +1,6 @@
 -- merged file : lualibs-basic-merged.lua
 -- parent file : lualibs-basic.lua
--- merge date  : 2020-05-01 15:49
+-- merge date  : Mon Aug 31 23:16:26 2020
 
 do -- begin closure to overcome local limits and interference
 
@@ -99,9 +99,6 @@ function optionalrequire(...)
   return result
  end
 end
-if lua then
- lua.mask=load([[τεχ = 1]]) and "utf" or "ascii"
-end
 local flush=io.flush
 if flush then
  local execute=os.execute if execute then function os.execute(...) flush() return execute(...) end end
@@ -397,19 +394,22 @@ function helpers.loaded(name)
  level=level+1
  for i=1,#sequence do
   local method=sequence[i]
-  if helpers.trace then
-   helpers.report("%s, level '%s', method '%s', name '%s'","locating",level,method,name)
-  end
-  local result,rest=methods[method](name)
-  if type(result)=="function" then
+  local lookup=method and methods[method]
+  if type(lookup)=="function" then
    if helpers.trace then
-    helpers.report("%s, level '%s', method '%s', name '%s'","found",level,method,name)
+    helpers.report("%s, level '%s', method '%s', name '%s'","locating",level,method,name)
    end
-   if helpers.traceused then
-    used[#used+1]={ level=level,name=name }
+   local result,rest=lookup(name)
+   if type(result)=="function" then
+    if helpers.trace then
+     helpers.report("%s, level '%s', method '%s', name '%s'","found",level,method,name)
+    end
+    if helpers.traceused then
+     used[#used+1]={ level=level,name=name }
+    end
+    level=level-1
+    return result,rest
    end
-   level=level-1
-   return result,rest
   end
  end
  level=level-1
@@ -542,11 +542,13 @@ local fullstripper=whitespace^0*C((whitespace^0*nonwhitespace^1)^0)
 local collapser=Cs(spacer^0/""*nonspacer^0*((spacer^0/" "*nonspacer^1)^0))
 local nospacer=Cs((whitespace^1/""+nonwhitespace^1)^0)
 local b_collapser=Cs(whitespace^0/""*(nonwhitespace^1+whitespace^1/" ")^0)
-local e_collapser=Cs((whitespace^1*endofstring/""+nonwhitespace^1+whitespace^1/" ")^0)
 local m_collapser=Cs((nonwhitespace^1+whitespace^1/" ")^0)
+local e_collapser=Cs((whitespace^1*endofstring/""+nonwhitespace^1+whitespace^1/" ")^0)
+local x_collapser=Cs((nonwhitespace^1+whitespace^1/"" )^0)
 local b_stripper=Cs(spacer^0/""*(nonspacer^1+spacer^1/" ")^0)
-local e_stripper=Cs((spacer^1*endofstring/""+nonspacer^1+spacer^1/" ")^0)
 local m_stripper=Cs((nonspacer^1+spacer^1/" ")^0)
+local e_stripper=Cs((spacer^1*endofstring/""+nonspacer^1+spacer^1/" ")^0)
+local x_stripper=Cs((nonspacer^1+spacer^1/"" )^0)
 patterns.stripper=stripper
 patterns.fullstripper=fullstripper
 patterns.collapser=collapser
@@ -554,9 +556,11 @@ patterns.nospacer=nospacer
 patterns.b_collapser=b_collapser
 patterns.m_collapser=m_collapser
 patterns.e_collapser=e_collapser
+patterns.x_collapser=x_collapser
 patterns.b_stripper=b_stripper
 patterns.m_stripper=m_stripper
 patterns.e_stripper=e_stripper
+patterns.x_stripper=x_stripper
 patterns.lowercase=lowercase
 patterns.uppercase=uppercase
 patterns.letter=patterns.lowercase+patterns.uppercase
@@ -3525,11 +3529,19 @@ local function isleapyear(year)
 end
 os.isleapyear=isleapyear
 local days={ 31,28,31,30,31,30,31,31,30,31,30,31 }
-local function nofdays(year,month)
+local function nofdays(year,month,day)
  if not month then
   return isleapyear(year) and 365 or 364
- else
+ elseif not day then
   return month==2 and isleapyear(year) and 29 or days[month]
+ else
+  for i=1,month-1 do
+   day=day+days[i]
+  end
+  if month>2 and isleapyear(year) then
+   day=day+1
+  end
+  return day
  end
 end
 os.nofdays=nofdays
@@ -4665,6 +4677,7 @@ do -- begin closure to overcome local limits and interference
 
 if not modules then modules={} end modules ['l-unicode']={
  version=1.001,
+ optimize=true,
  comment="companion to luat-lib.mkiv",
  author="Hans Hagen, PRAGMA-ADE, Hasselt NL",
  copyright="PRAGMA ADE / ConTeXt Development Team",
diff --git a/lualibs-extended-merged.lua b/lualibs-extended-merged.lua
index 2c6ab0c..89d384a 100644
--- a/lualibs-extended-merged.lua
+++ b/lualibs-extended-merged.lua
@@ -1,6 +1,6 @@
 -- merged file : lualibs-extended-merged.lua
 -- parent file : lualibs-extended.lua
--- merge date  : 2020-05-01 15:49
+-- merge date  : Mon Aug 31 23:16:16 2020
 
 do -- begin closure to overcome local limits and interference
 
@@ -658,33 +658,36 @@ local format_extension=function(extensions,f,name)
  local extension=extensions[name] or "tostring(%s)"
  local f=tonumber(f) or 1
  local w=find(extension,"%.%.%.")
- if w then
-  if f==0 then
+ if f==0 then
+  if w then
    extension=gsub(extension,"%.%.%.","")
-   return extension
-  elseif f==1 then
+  end
+  return extension
+ elseif f==1 then
+  if w then
    extension=gsub(extension,"%.%.%.","%%s")
-   n=n+1
-   local a="a"..n
-   return format(extension,a,a) 
-  elseif f<0 then
+  end
+  n=n+1
+  local a="a"..n
+  return format(extension,a,a) 
+ elseif f<0 then
+  if w then
+   extension=gsub(extension,"%.%.%.","")
+   return extension
+  else
    local a="a"..(n+f+1)
    return format(extension,a,a)
-  else
-   extension=gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
-   local t={}
-   for i=1,f do
-    n=n+1
-    t[i]="a"..n
-   end
-   return format(extension,unpack(t))
   end
  else
-  extension=gsub(extension,"%%s",function()
+  if w then
+   extension=gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
+  end
+  local t={}
+  for i=1,f do
    n=n+1
-   return "a"..n
-  end)
-  return extension
+   t[i]="a"..n
+  end
+  return format(extension,unpack(t))
  end
 end
 local builder=Cs { "start",
@@ -2096,7 +2099,7 @@ local lpeg,table,string=lpeg,table,string
 local P,R,V,S,C,Ct,Cs,Carg,Cc,Cg,Cf,Cp=lpeg.P,lpeg.R,lpeg.V,lpeg.S,lpeg.C,lpeg.Ct,lpeg.Cs,lpeg.Carg,lpeg.Cc,lpeg.Cg,lpeg.Cf,lpeg.Cp
 local lpegmatch,lpegpatterns=lpeg.match,lpeg.patterns
 local concat,gmatch,find=table.concat,string.gmatch,string.find
-local tostring,type,next,rawset=tostring,type,next,rawset
+local tonumber,tostring,type,next,rawset=tonumber,tostring,type,next,rawset
 local mod,div=math.mod,math.div
 utilities=utilities or {}
 local parsers=utilities.parsers or {}
@@ -2488,13 +2491,15 @@ function parsers.csvsplitter(specification)
  specification=specification and setmetatableindex(specification,defaultspecification) or defaultspecification
  local separator=specification.separator
  local quotechar=specification.quote
+ local numbers=specification.numbers
  local separator=S(separator~="" and separator or ",")
  local whatever=C((1-separator-newline)^0)
  if quotechar and quotechar~="" then
   local quotedata=nil
   for chr in gmatch(quotechar,".") do
    local quotechar=P(chr)
-   local quoteword=quotechar*C((1-quotechar)^0)*quotechar
+   local quoteitem=(1-quotechar)^0
+   local quoteword=quotechar*(numbers and (quoteitem/tonumber) or C(quoteitem))*quotechar
    if quotedata then
     quotedata=quotedata+quoteword
    else
@@ -2510,12 +2515,14 @@ function parsers.csvsplitter(specification)
 end
 function parsers.rfc4180splitter(specification)
  specification=specification and setmetatableindex(specification,defaultspecification) or defaultspecification
+ local numbers=specification.numbers
  local separator=specification.separator 
  local quotechar=P(specification.quote)  
  local dquotechar=quotechar*quotechar   
 /specification.quote
  local separator=S(separator~="" and separator or ",")
- local escaped=quotechar*Cs((dquotechar+(1-quotechar))^0)*quotechar
+ local whatever=(dquotechar+(1-quotechar))^0
+ local escaped=quotechar*(numbers and (whatever/tonumber) or Cs(whatever))*quotechar
  local non_escaped=C((1-quotechar-newline-separator)^1)
  local field=escaped+non_escaped+Cc("")
  local record=Ct(field*(separator*field)^1)
@@ -3389,18 +3396,11 @@ function statistics.show()
    return format("%s, type: %s, binary subtree: %s",
     os.platform or "unknown",os.type or "unknown",environment.texos or "unknown")
   end)
-  if LUATEXENGINE=="luametatex" then
-   register("used engine",function()
-    return format("%s version: %s, functionality level: %s, format id: %s, compiler: %s",
-     LUATEXENGINE,LUATEXVERSION,LUATEXFUNCTIONALITY,LUATEXFORMATID,status.used_compiler)
-   end)
-  else
-   register("used engine",function()
-    return format("%s version: %s, functionality level: %s, banner: %s",
-     LUATEXENGINE,LUATEXVERSION,LUATEXFUNCTIONALITY,lower(status.banner))
-   end)
-  end
-  register("control sequences",function()
+  register("used engine",function()
+   return format("%s version: %s, functionality level: %s, banner: %s",
+    LUATEXENGINE,LUATEXVERSION,LUATEXFUNCTIONALITY,lower(status.banner))
+  end)
+  register("used hash slots",function()
    return format("%s of %s + %s",status.cs_count,status.hash_size,status.hash_extra)
   end)
   register("callbacks",statistics.callbacks)
@@ -3414,15 +3414,10 @@ function statistics.show()
    end
   end
   register("lua properties",function()
-   local hashchar=tonumber(status.luatex_hashchars)
-   local mask=lua.mask or "ascii"
+   local hash=2^status.luatex_hashchars
+   local mask=load([[τεχ = 1]]) and "utf" or "ascii"
    return format("engine: %s %s, used memory: %s, hash chars: min(%i,40), symbol mask: %s (%s)",
-    jit and "luajit" or "lua",
-    LUAVERSION,
-    statistics.memused(),
-    hashchar and 2^hashchar or "unknown",
-    mask,
-    mask=="utf" and "τεχ" or "tex")
+    jit and "luajit" or "lua",LUAVERSION,statistics.memused(),hash,mask,mask=="utf" and "τεχ" or "tex")
   end)
   register("runtime",statistics.runtime)
   logs.newline() 
@@ -3478,6 +3473,13 @@ function statistics.tracefunction(base,tag,...)
   statistics.register(formatters["%s.%s"](tag,name),function() return serialize(stat,"calls") end)
  end
 end
+function status.getreadstate()
+ return {
+  filename=status.filename   or "?",
+  linenumber=status.linenumber or 0,
+  iocode=status.inputid or 0,
+ }
+end
 
 end -- closure
 
diff --git a/lualibs-lpeg.lua b/lualibs-lpeg.lua
index 7979a40..b0868ba 100644
--- a/lualibs-lpeg.lua
+++ b/lualibs-lpeg.lua
@@ -203,12 +203,14 @@ local collapser        = Cs(spacer^0/"" * nonspacer^0 * ((spacer^0/" " * nonspac
 local nospacer         = Cs((whitespace^1/"" + nonwhitespace^1)^0)
 
 local b_collapser      = Cs( whitespace^0              /"" * (nonwhitespace^1 + whitespace^1/" ")^0)
-local e_collapser      = Cs((whitespace^1 * endofstring/"" +  nonwhitespace^1 + whitespace^1/" ")^0)
 local m_collapser      = Cs(                                 (nonwhitespace^1 + whitespace^1/" ")^0)
+local e_collapser      = Cs((whitespace^1 * endofstring/"" +  nonwhitespace^1 + whitespace^1/" ")^0)
+local x_collapser      = Cs(                                 (nonwhitespace^1 + whitespace^1/"" )^0)
 
 local b_stripper       = Cs( spacer^0              /"" * (nonspacer^1 + spacer^1/" ")^0)
-local e_stripper       = Cs((spacer^1 * endofstring/"" +  nonspacer^1 + spacer^1/" ")^0)
 local m_stripper       = Cs(                             (nonspacer^1 + spacer^1/" ")^0)
+local e_stripper       = Cs((spacer^1 * endofstring/"" +  nonspacer^1 + spacer^1/" ")^0)
+local x_stripper       = Cs(                             (nonspacer^1 + spacer^1/"" )^0)
 
 patterns.stripper      = stripper
 patterns.fullstripper  = fullstripper
@@ -218,10 +220,12 @@ patterns.nospacer      = nospacer
 patterns.b_collapser   = b_collapser
 patterns.m_collapser   = m_collapser
 patterns.e_collapser   = e_collapser
+patterns.x_collapser   = x_collapser
 
 patterns.b_stripper    = b_stripper
 patterns.m_stripper    = m_stripper
 patterns.e_stripper    = e_stripper
+patterns.x_stripper    = x_stripper
 
 patterns.lowercase     = lowercase
 patterns.uppercase     = uppercase
diff --git a/lualibs-lua.lua b/lualibs-lua.lua
index f411230..00989c5 100644
--- a/lualibs-lua.lua
+++ b/lualibs-lua.lua
@@ -195,12 +195,6 @@ function optionalrequire(...)
     end
 end
 
--- nice for non ascii scripts (this might move):
-
-if lua then
-    lua.mask = load([[τεχ = 1]]) and "utf" or "ascii"
-end
-
 local flush = io.flush
 
 if flush then
diff --git a/lualibs-os.lua b/lualibs-os.lua
index 9aa8b8a..1e01350 100644
--- a/lualibs-os.lua
+++ b/lualibs-os.lua
@@ -604,11 +604,19 @@ os.isleapyear = isleapyear
 
 local days = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }
 
-local function nofdays(year,month)
+local function nofdays(year,month,day)
     if not month then
         return isleapyear(year) and 365 or 364
-    else
+    elseif not day then
         return month == 2 and isleapyear(year) and 29 or days[month]
+    else
+        for i=1,month-1 do
+            day = day + days[i]
+        end
+        if month > 2 and isleapyear(year) then
+            day = day + 1
+        end
+        return day
     end
 end
 
diff --git a/lualibs-package.lua b/lualibs-package.lua
index 0dd71e5..94607d4 100644
--- a/lualibs-package.lua
+++ b/lualibs-package.lua
@@ -54,7 +54,7 @@ local function lualibfile(name)
     return lpegmatch(pattern,name) or name
 end
 
-local offset = luarocks and 1 or 0 -- todo: also check other extras
+local offset = luarocks and 1 or 0 -- todo: also check other extras ... we'll drop this luarocks anyway
 
 local helpers = package.helpers or {
     cleanpath  = cleanpath,
@@ -346,19 +346,22 @@ function helpers.loaded(name)
     level = level + 1
     for i=1,#sequence do
         local method = sequence[i]
-        if helpers.trace then
-            helpers.report("%s, level '%s', method '%s', name '%s'","locating",level,method,name)
-        end
-        local result, rest = methods[method](name)
-        if type(result) == "function" then
+        local lookup = method and methods[method]
+        if type(lookup) == "function" then
             if helpers.trace then
-                helpers.report("%s, level '%s', method '%s', name '%s'","found",level,method,name)
+                helpers.report("%s, level '%s', method '%s', name '%s'","locating",level,method,name)
             end
-            if helpers.traceused then
-                used[#used+1] = { level = level, name = name }
+            local result, rest = lookup(name)
+            if type(result) == "function" then
+                if helpers.trace then
+                    helpers.report("%s, level '%s', method '%s', name '%s'","found",level,method,name)
+                end
+                if helpers.traceused then
+                    used[#used+1] = { level = level, name = name }
+                end
+                level = level - 1
+                return result, rest
             end
-            level = level - 1
-            return result, rest
         end
     end
     -- safeguard, we never come here
diff --git a/lualibs-trac-inf.lua b/lualibs-trac-inf.lua
index 244ba46..3db912b 100644
--- a/lualibs-trac-inf.lua
+++ b/lualibs-trac-inf.lua
@@ -223,21 +223,11 @@ function statistics.show()
             return format("%s, type: %s, binary subtree: %s",
                 os.platform or "unknown",os.type or "unknown", environment.texos or "unknown")
         end)
-     -- register("luatex banner", function()
-     --     return lower(status.banner)
-     -- end)
-        if LUATEXENGINE == "luametatex" then
-            register("used engine", function()
-                return format("%s version: %s, functionality level: %s, format id: %s, compiler: %s",
-                    LUATEXENGINE, LUATEXVERSION, LUATEXFUNCTIONALITY, LUATEXFORMATID, status.used_compiler)
-            end)
-        else
-            register("used engine", function()
-                return format("%s version: %s, functionality level: %s, banner: %s",
-                    LUATEXENGINE, LUATEXVERSION, LUATEXFUNCTIONALITY, lower(status.banner))
-            end)
-        end
-        register("control sequences", function()
+        register("used engine", function()
+            return format("%s version: %s, functionality level: %s, banner: %s",
+                LUATEXENGINE, LUATEXVERSION, LUATEXFUNCTIONALITY, lower(status.banner))
+        end)
+        register("used hash slots", function()
             return format("%s of %s + %s", status.cs_count, status.hash_size,status.hash_extra)
         end)
         register("callbacks", statistics.callbacks)
@@ -251,17 +241,11 @@ function statistics.show()
             end
         end
         -- so far
-     -- collectgarbage("collect")
         register("lua properties",function()
-            local hashchar = tonumber(status.luatex_hashchars)
-            local mask = lua.mask or "ascii"
+            local hash = 2^status.luatex_hashchars
+            local mask = load([[τεχ = 1]]) and "utf" or "ascii"
             return format("engine: %s %s, used memory: %s, hash chars: min(%i,40), symbol mask: %s (%s)",
-                jit and "luajit" or "lua",
-                LUAVERSION,
-                statistics.memused(),
-                hashchar and 2^hashchar or "unknown",
-                mask,
-                mask == "utf" and "τεχ" or "tex")
+                jit and "luajit" or "lua", LUAVERSION, statistics.memused(), hash, mask, mask == "utf" and "τεχ" or "tex")
         end)
         register("runtime",statistics.runtime)
         logs.newline() -- initial newline
@@ -328,3 +312,12 @@ function statistics.tracefunction(base,tag,...)
         statistics.register(formatters["%s.%s"](tag,name),function() return serialize(stat,"calls") end)
     end
 end
+
+function status.getreadstate()
+    return {
+        filename   = status.filename   or "?",
+        linenumber = status.linenumber or 0,
+        iocode     = status.inputid    or 0,
+    }
+end
+
diff --git a/lualibs-unicode.lua b/lualibs-unicode.lua
index 2708d14..5d9a714 100644
--- a/lualibs-unicode.lua
+++ b/lualibs-unicode.lua
@@ -1,5 +1,6 @@
 if not modules then modules = { } end modules ['l-unicode'] = {
     version   = 1.001,
+    optimize  = true,
     comment   = "companion to luat-lib.mkiv",
     author    = "Hans Hagen, PRAGMA-ADE, Hasselt NL",
     copyright = "PRAGMA ADE / ConTeXt Development Team",
diff --git a/lualibs-util-prs.lua b/lualibs-util-prs.lua
index 3154bf6..6d2f8c1 100644
--- a/lualibs-util-prs.lua
+++ b/lualibs-util-prs.lua
@@ -10,7 +10,7 @@ local lpeg, table, string = lpeg, table, string
 local P, R, V, S, C, Ct, Cs, Carg, Cc, Cg, Cf, Cp = lpeg.P, lpeg.R, lpeg.V, lpeg.S, lpeg.C, lpeg.Ct, lpeg.Cs, lpeg.Carg, lpeg.Cc, lpeg.Cg, lpeg.Cf, lpeg.Cp
 local lpegmatch, lpegpatterns = lpeg.match, lpeg.patterns
 local concat, gmatch, find = table.concat, string.gmatch, string.find
-local tostring, type, next, rawset = tostring, type, next, rawset
+local tonumber, tostring, type, next, rawset = tonumber, tostring, type, next, rawset
 local mod, div = math.mod, math.div
 
 utilities         = utilities or {}
@@ -373,6 +373,8 @@ hashes.settings_to_set =  table.setmetatableindex(function(t,k) -- experiment, n
     return v
 end)
 
+-- 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)
 
 function parsers.simple_hash_to_string(h, separator)
@@ -538,13 +540,15 @@ function parsers.csvsplitter(specification)
     specification   = specification and setmetatableindex(specification,defaultspecification) or defaultspecification
     local separator = specification.separator
     local quotechar = specification.quote
+    local numbers   = specification.numbers
     local separator = S(separator ~= "" and separator or ",")
     local whatever  = C((1 - separator - newline)^0)
     if quotechar and quotechar ~= "" then
         local quotedata = nil
         for chr in gmatch(quotechar,".") do
             local quotechar = P(chr)
-            local quoteword = quotechar * C((1 - quotechar)^0) * quotechar
+            local quoteitem = (1 - quotechar)^0
+            local quoteword = quotechar * (numbers and (quoteitem/tonumber) or C(quoteitem)) * quotechar
             if quotedata then
                 quotedata = quotedata + quoteword
             else
@@ -559,29 +563,29 @@ function parsers.csvsplitter(specification)
     end
 end
 
--- and this is a slightly patched version of a version posted by Philipp Gesang
-
--- local mycsvsplitter = parsers.rfc4180splitter()
-
 -- local crap = [[
 -- first,second,third,fourth
 -- "1","2","3","4"
--- "a","b","c","d"
--- "foo","bar""baz","boogie","xyzzy"
+-- "5","6","7","8"
 -- ]]
+--
+-- local mycsvsplitter = parsers.csvsplitter { numbers = true }
+--
+-- local list = mycsvsplitter(crap) inspect(list)
 
--- local list, names = mycsvsplitter(crap,true)   inspect(list) inspect(names)
--- local list, names = mycsvsplitter(crap)        inspect(list) inspect(names)
+-- and this is a slightly patched version of a version posted by Philipp Gesang
 
 function parsers.rfc4180splitter(specification)
     specification     = specification and setmetatableindex(specification,defaultspecification) or defaultspecification
+    local numbers     = specification.numbers
     local separator   = specification.separator --> rfc: COMMA
     local quotechar   = P(specification.quote)  -->      DQUOTE
     local dquotechar  = quotechar * quotechar   -->      2DQUOTE
                       / specification.quote
     local separator   = S(separator ~= "" and separator or ",")
+    local whatever    = (dquotechar + (1 - quotechar))^0
     local escaped     = quotechar
-                      * Cs((dquotechar + (1 - quotechar))^0)
+                      * (numbers and (whatever/tonumber) or Cs(whatever))
                       * quotechar
     local non_escaped = C((1 - quotechar - newline - separator)^1)
     local field       = escaped + non_escaped + Cc("")
@@ -601,6 +605,18 @@ function parsers.rfc4180splitter(specification)
     end
 end
 
+-- local mycsvsplitter = parsers.rfc4180splitter { numbers = true }
+--
+-- local crap = [[
+-- first,second,third,fourth
+-- "1","2","3","4"
+-- "a","b","c","d"
+-- "foo","bar""baz","boogie","xyzzy"
+-- ]]
+--
+-- local list, names = mycsvsplitter(crap,true)   inspect(list) inspect(names)
+-- local list, names = mycsvsplitter(crap)        inspect(list) inspect(names)
+
 -- parsers.stepper("1,7-",9,function(i) print(">>>",i) end)
 -- parsers.stepper("1-3,7,8,9")
 -- parsers.stepper("1-3,6,7",function(i) print(">>>",i) end)
diff --git a/lualibs-util-str.lua b/lualibs-util-str.lua
index aba7859..2d3f4d6 100644
--- a/lualibs-util-str.lua
+++ b/lualibs-util-str.lua
@@ -1057,76 +1057,44 @@ local format_rest = function(s)
     return format("%q",s) -- catches " and \n and such
 end
 
--- local format_extension = function(extensions,f,name)
---     local extension = extensions[name] or "tostring(%s)"
---     local f = tonumber(f) or 1
---     local w = find(extension,"%.%.%.")
---     if f == 0 then
---         if w then
---             extension = gsub(extension,"%.%.%.","")
---         end
---         return extension
---     elseif f == 1 then
---         if w then
---             extension = gsub(extension,"%.%.%.","%%s")
---         end
---         n = n + 1
---         local a = "a" .. n
---         return format(extension,a,a) -- maybe more times?
---     elseif f < 0 then
---         local a = "a" .. (n + f + 1)
---         return format(extension,a,a)
---     else
---         if w then
---             extension = gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
---         end
---         -- we could fill an array and then n = n + 1 unpack(t,n,n+f) but as we
---         -- cache we don't save much and there are hardly any extensions anyway
---         local t = { }
---         for i=1,f do
---             n = n + 1
---          -- t[#t+1] = "a" .. n
---             t[i] = "a" .. n
---         end
---         return format(extension,unpack(t))
---     end
--- end
-
 local format_extension = function(extensions,f,name)
     local extension = extensions[name] or "tostring(%s)"
     local f = tonumber(f) or 1
     local w = find(extension,"%.%.%.")
-    if w then
-        -- we have a wildcard
-        if f == 0 then
+    if f == 0 then
+        if w then
             extension = gsub(extension,"%.%.%.","")
-            return extension
-        elseif f == 1 then
+        end
+        return extension
+    elseif f == 1 then
+        if w then
             extension = gsub(extension,"%.%.%.","%%s")
-            n = n + 1
-            local a = "a" .. n
-            return format(extension,a,a) -- maybe more times?
-        elseif f < 0 then
+        end
+        n = n + 1
+        local a = "a" .. n
+        return format(extension,a,a) -- maybe more times?
+    elseif f < 0 then
+        if w then
+            -- not supported
+            extension = gsub(extension,"%.%.%.","")
+            return extension
+        else
             local a = "a" .. (n + f + 1)
             return format(extension,a,a)
-        else
-            extension = gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
-            -- we could fill an array and then n = n + 1 unpack(t,n,n+f) but as we
-            -- cache we don't save much and there are hardly any extensions anyway
-            local t = { }
-            for i=1,f do
-                n = n + 1
-             -- t[#t+1] = "a" .. n
-                t[i] = "a" .. n
-            end
-            return format(extension,unpack(t))
         end
     else
-        extension = gsub(extension,"%%s",function()
+        if w then
+            extension = gsub(extension,"%.%.%.",rep("%%s,",f-1).."%%s")
+        end
+        -- we could fill an array and then n = n + 1 unpack(t,n,n+f) but as we
+        -- cache we don't save much and there are hardly any extensions anyway
+        local t = { }
+        for i=1,f do
             n = n + 1
-            return "a" .. n
-        end)
-        return extension
+         -- t[#t+1] = "a" .. n
+            t[i] = "a" .. n
+        end
+        return format(extension,unpack(t))
     end
 end
 
diff --git a/lualibs-util-tab.lua b/lualibs-util-tab.lua
index 4dafb2a..9f7112e 100644
--- a/lualibs-util-tab.lua
+++ b/lualibs-util-tab.lua
@@ -961,3 +961,12 @@ function table.ordered(t)
         return function() end
     end
 end
+
+-- function table.randomremove(t,n)
+--     if not n then
+--         n = #t
+--     end
+--     if n > 0 then
+--         return remove(t,random(1,n))
+--     end
+-- end
diff --git a/lualibs.dtx b/lualibs.dtx
index e93eaac..c98c752 100644
--- a/lualibs.dtx
+++ b/lualibs.dtx
@@ -37,7 +37,7 @@
 \input docstrip.tex
 \Msg{************************************************************************}
 \Msg{* Installation}
-\Msg{* Package: lualibs 2020-05-01 v2.71 Lua additional functions.}
+\Msg{* Package: lualibs 2020-08-31 v2.72 Lua additional functions.}
 \Msg{************************************************************************}
 
 \keepsilent
@@ -107,7 +107,7 @@ and lualibs-extended.lua.
 %<*driver>
 \NeedsTeXFormat{LaTeX2e}
 \ProvidesFile{lualibs.drv}
-  [2020/05/01 v2.71 Lua Libraries.]
+  [2020/08/31 v2.72 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{2020/05/01 v2.71}
+% \date{2020/08/31 v2.72}
 % \author{Élie Roux      · \email{elie.roux at telecom-bretagne.eu}\\
 %         Philipp Gesang · \email{phg at phi-gamma.net}\\
 %         The \LaTeX3 Project · \email{https://github.com/latex3/lualibs/}\\
@@ -429,8 +429,8 @@ lualibs = lualibs or { }
 
 lualibs.module_info = {
   name          = "lualibs",
-  version       = "2.71",       --TAGVERSION
-    date        = "2020-05-01", --TAGDATE
+  version       = "2.72",       --TAGVERSION
+    date        = "2020-08-31", --TAGDATE
   description   = "ConTeXt Lua standard libraries.",
   author        = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
   copyright     = "PRAGMA ADE / ConTeXt Development Team",
@@ -583,8 +583,8 @@ local loadmodule        = lualibs.loadmodule
 
 local lualibs_basic_module = {
   name          = "lualibs-basic",
-  version       = "2.71",       --TAGVERSION
-  date          = "2020-05-01", --TAGDATE
+  version       = "2.72",       --TAGVERSION
+  date          = "2020-08-31", --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.71",       --TAGVERSION
-  date          = "2020-05-01", --TAGDATE
+  version       = "2.72",       --TAGVERSION
+  date          = "2020-08-31", --TAGDATE
   description   = "ConTeXt Lua libraries -- extended collection.",
   author        = "Hans Hagen, PRAGMA-ADE, Hasselt NL & Elie Roux & Philipp Gesang",
   copyright     = "PRAGMA ADE / ConTeXt Development Team",





More information about the latex3-commits mailing list.