Browse Source

* Add interface to libpcre (Perl Compatible Regular Expressions)

Michaël Van Canneyt 1 year ago
parent
commit
b61d85ad2d

+ 1 - 0
packages/fpmake_add.inc

@@ -145,6 +145,7 @@
   add_webidl(ADirectory+IncludeTrailingPathDelimiter('webidl'));
   add_gnutls(ADirectory+IncludeTrailingPathDelimiter('gnutls'));
   add_ide(ADirectory+IncludeTrailingPathDelimiter('ide'));
+  add_libpcre(ADirectory+IncludeTrailingPathDelimiter('libpcre'));
   add_vclcompat(ADirectory+IncludeTrailingPathDelimiter('vcl-compat'));
   add_qlunits(ADirectory+IncludeTrailingPathDelimiter('qlunits'));
   add_mustache(ADirectory+IncludeTrailingPathDelimiter('fcl-mustache'));

+ 7 - 0
packages/fpmake_proc.inc

@@ -833,6 +833,13 @@ begin
 {$include vcl-compat/fpmake.pp}
 end;
 
+procedure add_libpcre(const ADirectory: string);
+begin
+  with Installer do
+{$include libpcre/fpmake.pp}
+end;
+
+
 procedure add_qlunits(const ADirectory: string);
 begin
   with Installer do

+ 2 - 0
packages/libpcre/Makefile

@@ -0,0 +1,2 @@
+PACKAGE_NAME=libpcre
+include ../build/Makefile.pkg

+ 564 - 0
packages/libpcre/examples/tpcre.pp

@@ -0,0 +1,564 @@
+program tpcre;
+
+{$DEFINE USE_WIDESTRING}
+
+uses
+   {$IFNDEF USE_WIDESTRING}
+   libpcre2_8,
+   {$ELSE}
+   libpcre2_16,
+   {$ENDIF}
+   ctypes;
+
+
+{$IFNDEF USE_WIDESTRING}
+function GetStrLen(p : PAnsiChar; len : Integer) : AnsiString;
+
+begin
+  SetLength(Result,Len);
+  if Len>0 then
+    Move(P^,Result[1],Len);
+end;
+{$ELSE}
+function GetStrLen(p : PWideChar; len : Integer) : UnicodeString;
+
+begin
+  SetLength(Result,Len);
+  if Len>0 then
+    Move(P^,Result[1],Len*2);
+end;
+{$ENDIF}
+
+var
+ re : ppcre2_code;
+ {$IFNDEF USE_WIDESTRING}
+ ptrn : AnsiString;
+ subj : AnsiString;
+ {$ELSE}
+ ptrn : UnicodeString;
+ subj : UnicodeString;
+ {$ENDIF}
+
+ pattern : PCRE2_SPTR;     (* PCRE2_SPTR is a pointer to unsigned code units of *)
+ subject : PCRE2_SPTR;     (* the appropriate width (in this case, 8 bits). *)
+ name_table : PCRE2_SPTR;
+
+ utf8,
+ crlf_is_newline,
+ find_all : Boolean;
+ errornumber,
+ i,n,matchlen,
+ rc : cint;
+
+ newline,
+ name_entry_size,
+ namecount,
+ options,
+ option_bits : cuint32 ;
+
+ erroroffset : PCRE2_SIZE;
+ ovector : ^PCRE2_SIZE;
+ pattern_length,
+ subject_length : PCRE2_SIZE;
+
+ match_data : ppcre2_match_data;
+ buffer : Array[0..255] of ansichar;
+ substring_start : PCRE2_SPTR;
+ substring_length : PCRE2_SIZE;
+ tabptr: PCRE2_SPTR ;
+ start_offset : PCRE2_SIZE;
+ startchar : PCRE2_SIZE ;
+
+begin
+  (*
+    ***************************************************************************
+    * First, sort out the command line. There is only one possible option at  *
+    * the moment, "-g" to request repeated matching to find all occurrences,  *
+    * like Perl's /g option. We set the variable find_all to a non-zero value *
+    * if the -g option is present.                                            *
+  ***************************************************************************
+  *)
+
+  find_all:=False;
+  I:=1;
+  While I<=ParamCount do
+    begin
+    if (ParamStr(i)='-g') then
+      find_all:=True
+    else if (ParamStr(i)[1] = '-') then
+      begin
+      Writeln('Unrecognised option: ', paramstr(i));
+      halt(1);
+      end
+    else
+      Break;
+    Inc(I);
+    end;
+
+  (*
+    After the options, we require exactly two arguments, which are the pattern,
+    and the subject string.
+  *)
+
+  if ((ParamCount-i+1)<>2) then
+    begin
+    Writeln('Exactly two arguments required: a regex and a subject string');
+    Halt(1);
+    end;
+
+  (*
+    Pattern and subject are char arguments, so they can be straightforwardly
+    cast to PCRE2_SPTR because we are working in 8-bit code units. The subject
+    length is cast to PCRE2_SIZE for completeness, though PCRE2_SIZE is in fact
+    defined to be size_t.
+  *)
+
+  ptrn:=ParamStr(I);
+  subj:=ParamStr(I+1);
+  {$IFNDEF USE_WIDESTRING}
+  pattern:=PAnsiChar(ptrn);
+  subject:=PAnsiChar(Subj);
+  {$ELSE}
+  pattern:=PUnicodeChar(ptrn);
+  subject:=PUnicodeChar(Subj);
+  {$ENDIF}
+  pattern_length:=length(pattern);
+  subject_length:=Length(subject);
+
+
+  (*
+    **************************************************************************
+    * Now we are going to compile the regular expression pattern, and handle *
+    * any errors that are detected.                                          *
+    **************************************************************************
+  *)
+
+{$IFDEF USE_WIDESTRING}
+  re:=pcre2_compile_w(
+{$ELSE}
+  re:=pcre2_compile(
+{$ENDIF}
+    pattern, (* the pattern *)
+    pattern_length,        (* Pattern-length *)
+    0,                     (* default options *)
+    @errornumber,          (* for error number *)
+    @erroroffset,          (* for error offset *)
+    Nil);                 (* use default compile context *)
+
+  (*
+  Compilation failed: print the error message and exit.
+  *)
+
+  if (re=Nil) then
+    begin
+    pcre2_get_error_message(errornumber, @buffer, sizeof(buffer));
+    Writeln('PCRE2 compilation failed at offset ',erroroffset,': ',buffer);
+    halt(1)
+    end;
+
+
+  (*
+    **************************************************************************
+    * If the compilation succeeded, we call PCRE2 again, in order to do a    *
+    * pattern match against the subject string. This does just ONE match. If *
+    * further matching is needed, it will be done below. Before running the  *
+    * match we must set up a match_data block for holding the result. Using  *
+    * pcre2_match_data_create_from_pattern() ensures that the block is       *
+    * exactly the right size for the number of capturing parentheses in the  *
+    * pattern. If you need to know the actual size of a match_data block as  *
+    * a number of bytes, you can find it like this:                          *
+    *                                                                        *
+    * PCRE2_SIZE match_data_size = pcre2_get_match_data_size(match_data);    *
+    **************************************************************************
+  *)
+
+  match_data := pcre2_match_data_create_from_pattern(re, Nil);
+
+  (*
+    Now run the match.
+  *)
+
+  {$IFDEF USE_WIDESTRING}
+  rc := pcre2_match_w(
+  {$ELSE}
+  rc := pcre2_match(
+  {$ENDIF}
+    re,                   (* the compiled pattern *)
+    subject,              (* the subject string *)
+    subject_length,       (* the length of the subject *)
+    0,                    (* start at offset 0 in the subject *)
+    0,                    (* default options *)
+    match_data,           (* block for storing the result *)
+    Nil);                (* use default match context *)
+
+  (*
+    Matching failed: handle error cases
+  *)
+
+  if (rc < 0) then
+    begin
+    Case rc of
+      PCRE2_ERROR_NOMATCH: Writeln('No match');
+    else
+       Writeln('Matching error ', rc);
+    end;
+    pcre2_match_data_free(match_data);   (* Release memory used for the match *)
+    pcre2_code_free(re);                 (*   data and the compiled pattern. *)
+    Halt(1);
+    end;
+
+  (*
+    Match succeeded. Get a pointer to the output vector, where string offsets
+    are stored.
+  *)
+
+  ovector := pcre2_get_ovector_pointer(match_data);
+  Writeln('Match succeeded at offset ', integer(ovector[0]));
+
+
+  (*
+    **************************************************************************
+    * We have found the first match within the subject string. If the output *
+    * vector wasn't big enough, say so. Then output any substrings that were *
+    * captured.                                                              *
+  **************************************************************************
+  *)
+
+  (*
+    The output vector wasn't big enough. This should not happen, because we used
+    pcre2_match_data_create_from_pattern() above.
+  *)
+
+  if (rc = 0) then
+    Writeln('ovector was not big enough for all the captured substrings');
+
+  (*
+    Since release 10.38 PCRE2 has locked out the use of \K in lookaround
+    assertions. However, there is an option to re-enable the old behaviour. If that
+    is set, it is possible to run patterns such as /(?=.\K)/ that use \K in an
+    assertion to set the start of a match later than its end. In this demonstration
+    program, we show how to detect this case, but it shouldn't arise because the
+    option is never set.
+  *)
+
+  if (ovector[0] > ovector[1]) then
+    begin
+    i:=integer(ovector[0] - ovector[1]);
+    Writeln('\K was used in an assertion to set the match start after its end.',
+            'From end to start the match was:', GetStrLen(subject+ovector[1],i));
+    Writeln('Run abandoned');
+    pcre2_match_data_free(match_data);
+    pcre2_code_free(re);
+    Halt(1);
+    end;
+
+  (*
+    Show substrings stored in the output vector by number. Obviously, in a real
+    application you might want to do things other than print them.
+  *)
+
+  for i:=0 to rc-1 do
+    begin
+    substring_start := subject + ovector[2*i];
+    substring_length := ovector[2*i+1] - ovector[2*i];
+    Writeln(i:2, ': ',GetStrLen(substring_start,substring_length));
+    end ;
+
+
+  (*
+    ***************************************************************************
+    * That concludes the basic part of this demonstration program. We have    *
+    * compiled a pattern, and performed a single match. The code that follows *
+    * shows first how to access named substrings, and then how to code for    *
+    * repeated matches on the same subject.                                   *
+    ***************************************************************************
+  *)
+
+  (*
+    See if there are any named substrings, and if so, show them by name.
+    First we have to extract the count of named parentheses from the pattern.
+  *)
+
+  pcre2_pattern_info(
+    re,                   (* the compiled pattern *)
+    PCRE2_INFO_NAMECOUNT, (* get the number of named substrings *)
+    @namecount);          (* where to put the answer *)
+
+  if (namecount = 0) then
+    Writeln('No named substrings')
+  else
+    begin
+    Writeln('Named substrings');
+
+    (*
+      Before we can access the substrings, we must extract the table for
+      translating names to numbers, and the size of each entry in the table.
+    *)
+
+    pcre2_pattern_info(
+      re,                       (* the compiled pattern *)
+      PCRE2_INFO_NAMETABLE,     (* address of the table *)
+      @name_table);             (* where to put the answer *)
+
+    pcre2_pattern_info(
+      re,                       (* the compiled pattern *)
+      PCRE2_INFO_NAMEENTRYSIZE, (* size of each entry in the table *)
+      @name_entry_size);        (* where to put the answer *)
+
+    (*
+      Now we can scan the table and, for each entry, print the number, the name,
+      and the substring itself. In the 8-bit library the number is held in two
+      bytes, most significant first.
+    *)
+
+    tabptr := name_table;
+    for i:=0 to namecount-1 do
+      begin
+      n:=(ord(tabptr[0]) shl 8) or ord(tabptr[1]);
+      matchlen:=integer(ovector[2*n+1] - ovector[2*n]);
+      writeln( '(',n,')', GetStrLen((tabptr + 2),name_entry_size - 3),' : ',
+                          GetStrLen((subject + ovector[2*n]), Matchlen));
+      inc(tabptr, name_entry_size);
+      end ;
+    end  ;
+
+
+  (*
+    **************************************************************************
+    * If the '-g' option was given on the command line, we want to continue  *
+    * to search for additional matches in the subject string, in a similar   *
+    * way to the /g option in Perl. This turns out to be trickier than you   *
+    * might think because of the possibility of matching an empty string.    *
+    * What happens is as follows:                                            *
+    *                                                                        *
+    * If the previous match was NOT for an empty string, we can just start   *
+    * the next match at the end of the previous one.                         *
+    *                                                                        *
+    * If the previous match WAS for an empty string, we can't do that, as it *
+    * would lead to an infinite loop. Instead, a call of pcre2_match() is    *
+    * made with the PCRE2_NOTEMPTY_ATSTART and PCRE2_ANCHORED flags set. The *
+    * first of these tells PCRE2 that an empty string at the start of the    *
+    * subject is not a valid match; other possibilities must be tried. The   *
+    * second flag restricts PCRE2 to one match attempt at the initial string *
+    * position. If this match succeeds, an alternative to the empty string   *
+    * match has been found, and we can print it and proceed round the loop,  *
+    * advancing by the length of whatever was found. If this match does not  *
+    * succeed, we still stay in the loop, advancing by just one character.   *
+    * In UTF-8 mode, which can be set by ( *UTF) in the pattern, this may be *
+    * more than one byte.                                                    *
+    *                                                                        *
+    * However, there is a complication concerned with newlines. When the     *
+    * newline convention is such that CRLF is a valid newline, we must       *
+    * advance by two characters rather than one. The newline convention can  *
+    * be set in the regex by ( *CR), etc.; if not, we must find the default. *
+    **************************************************************************
+  *)
+
+  if Not find_all then    (* Check for -g *)
+    begin
+    pcre2_match_data_free(match_data);  (* Release the memory that was used *)
+    pcre2_code_free(re);                (* for the match data and the pattern. *)
+    Halt(0);                           (* Exit the program. *)
+    end ;
+
+  (*
+    Before running the loop, check for UTF-8 and whether CRLF is a valid newline
+    sequence. First, find the options with which the regex was compiled and extract
+    the UTF state.
+  *)
+
+  pcre2_pattern_info(re, PCRE2_INFO_ALLOPTIONS, @option_bits);
+  utf8 := ((option_bits and PCRE2_UTF) <> 0);
+
+  (*
+    Now find the newline convention and see whether CRLF is a valid newline
+    sequence.
+  *)
+
+  pcre2_pattern_info(re, PCRE2_INFO_NEWLINE, @newline);
+  crlf_is_newline :=  (newline = PCRE2_NEWLINE_ANY) or
+                      (newline = PCRE2_NEWLINE_CRLF) or
+                      (newline = PCRE2_NEWLINE_ANYCRLF);
+
+(* Loop for second and subsequent matches *)
+
+  While true do
+    begin
+    options := 0;                   (* Normally no options *)
+    start_offset := ovector[1];   (* Start at end of previous match *)
+
+    (*
+      If the previous match was for an empty string, we are finished if we are
+      at the end of the subject. Otherwise, arrange to run another match at the
+      same point to see if a non-empty match can be found.
+    *)
+
+    if (ovector[0] = ovector[1]) then
+      begin
+      if (ovector[0] = subject_length) then
+        break;
+      options := PCRE2_NOTEMPTY_ATSTART or PCRE2_ANCHORED;
+      end
+
+    (*
+      If the previous match was not an empty string, there is one tricky case to
+      consider. If a pattern contains \K within a lookbehind assertion at the
+      start, the end of the matched string can be at the offset where the match
+      started. Without special action, this leads to a loop that keeps on matching
+      the same substring. We must detect this case and arrange to move the start on
+      by one character. The pcre2_get_startchar() function returns the starting
+      offset that was passed to pcre2_match().
+    *)
+
+    else
+      begin
+      startchar := pcre2_get_startchar(match_data);
+      if (start_offset <= startchar) then
+        begin
+        if (startchar >= subject_length) then
+          break;                                 (* Reached end of subject.   *)
+        start_offset:=startchar + 1;             (* Advance by one character. *)
+        if utf8 then                        (* If UTF-8, it may be more  *)
+          begin                                  (*   than one code unit.     *)
+          While (start_offset < subject_length) do
+            begin
+            if ((Ord(subject[start_offset]) and $c0) <> $80) then
+              break;
+            inc(start_offset);
+            end;
+          end
+        end
+      end ;
+
+    (*
+      Run the next matching operation
+    *)
+
+    {$IFDEF USE_WIDESTRING}
+    rc := pcre2_match_w(
+    {$ELSE}
+    rc := pcre2_match(
+    {$ENDIF}
+      re,                   (* the compiled pattern *)
+      subject,              (* the subject string *)
+      subject_length,       (* the length of the subject *)
+      start_offset,         (* starting offset in the subject *)
+      options,              (* options *)
+      match_data,           (* block for storing the result *)
+      Nil);                (* use default match context *)
+
+    (*
+      This time, a result of NOMATCH isn't an error. If the value in 'options'
+      is zero, it just means we have found all possible matches, so the loop ends.
+      Otherwise, it means we have failed to find a non-empty-string match at a
+      point where there was a previous empty-string match. In this case, we do what
+      Perl does: advance the matching position by one character, and continue. We
+      do this by setting the 'end of previous match' offset, because that is picked
+      up at the top of the loop as the point at which to start again.
+
+      There are two complications: (a) When CRLF is a valid newline sequence, and
+      the current position is just before it, advance by an extra byte. (b)
+      Otherwise we must ensure that we skip an entire UTF character if we are in
+      UTF mode.
+    *)
+
+    if (rc = PCRE2_ERROR_NOMATCH) then
+      begin
+      if (options = 0) then
+        break;                                     (* All matches found *)
+      ovector[1] := start_offset + 1;              (* Advance one code unit *)
+      if (crlf_is_newline) and                  (* If CRLF is a newline & *)
+          (start_offset < subject_length - 1) and  (* we are at CRLF, *)
+          (subject[start_offset] = #13) and
+          (subject[start_offset + 1] = #10) then
+        inc(ovector[1])                             (* Advance by one more. *)
+      else if (utf8) then                        (* Otherwise, ensure we *)
+        begin                                       (* advance a whole UTF-8 *)
+        while (ovector[1] < subject_length) do      (* character. *)
+          begin
+          if ((Ord(subject[ovector[1]]) and $c0) <> $80) then
+            break;
+          inc(ovector[1]);
+          end;
+        end;
+      continue;    (* Go round the loop again *)
+      end;
+
+    (*
+      Other matching errors are not recoverable.
+    *)
+
+    if (rc < 0) then
+      begin
+      Writeln('Matching error %d', rc);
+      pcre2_match_data_free(match_data);
+      pcre2_code_free(re);
+      Halt(1);
+      end;
+
+    (*
+      Match succeeded
+    *)
+
+    Writeln('Match succeeded again at offset ', integer (ovector[0]));
+
+    (*
+      The match succeeded, but the output vector wasn't big enough. This
+      should not happen.
+    *)
+
+    if (rc = 0) then
+      Writeln('ovector was not big enough for all the captured substrings');
+
+    (*
+      We must guard against patterns such as /(?=.\K)/ that use \K in an
+      assertion to set the start of a match later than its end. In this
+      demonstration program, we just detect this case and give up.
+    *)
+
+    if (ovector[0] > ovector[1]) then
+      begin
+      matchlen:=Integer(ovector[0] - ovector[1]);
+      writeln('\K was used in an assertion to set the match start after its end.');
+      Writeln('From end to start the match was: ', GetStrLen((subject + ovector[1]),matchlen));
+      writeln('Run abandoned');
+      pcre2_match_data_free(match_data);
+      pcre2_code_free(re);
+      Halt(1);
+      end ;
+
+    (*
+      As before, show substrings stored in the output vector by number, and then
+      also any named substrings.
+    *)
+
+    for i := 0 to rc-1 do
+      begin
+      substring_start:=subject + ovector[2*i];
+      substring_length:=ovector[2*i+1] - ovector[2*i];
+      Writeln(i,': ',GetStrLen(substring_start,substring_length));
+      end;
+
+    if (namecount = 0) then
+      Writeln('No named substrings')
+    else
+      begin
+      Writeln('Named substrings');
+      for i:=0 to namecount-1 do
+        begin
+        n := (Ord(tabptr[0]) shl 8) or ord(tabptr[1]);
+        writeln(n,': ',GetStrLen(tabptr + 2,name_entry_size - 3),'= ',
+                        GetStrLen(subject + ovector[2*n], integer(ovector[2*n+1] - ovector[2*n])));
+        tabptr := tabptr+name_entry_size;
+        end ;
+      end;
+    end ;
+  (*
+    End of loop to find second and subsequent matches
+  *)
+
+  Writeln('');
+  pcre2_match_data_free(match_data);
+  pcre2_code_free(re);
+end.
+

+ 51 - 0
packages/libpcre/fpmake.pp

@@ -0,0 +1,51 @@
+{$ifndef ALLPACKAGES}
+{$mode objfpc}{$H+}
+program fpmake;
+
+uses {$ifdef unix}cthreads,{$endif} fpmkunit;
+
+Var
+  P : TPackage;
+  T : TTarget;
+begin
+  With Installer do
+    begin
+{$endif ALLPACKAGES}
+
+    P:=AddPackage('libpcre');
+    P.ShortName:='pcre';
+{$ifdef ALLPACKAGES}
+    P.Directory:=ADirectory;
+{$endif ALLPACKAGES}
+    P.Version:='3.3.1';
+    P.Author := 'Library: PCRE';
+    P.License := 'Library: BSD License, header: LGPL with modification, ';
+    P.HomepageURL := 'www.freepascal.org';
+    P.Email := '';
+    P.Description := 'Headers for the PCRE (Perl Compatible Regular Expressions) library';
+    P.NeedLibC:= true;  // true for headers that indirectly link to libc?
+    P.OSes :=  [Win64,Linux,darwin];
+
+    P.SourcePath.Add('src');
+    P.IncludePath.Add('src');
+
+    T:=P.Targets.AddUnit('libpcre2_8.pp');
+      with T.Dependencies do
+        begin
+          AddInclude('pcreconst.inc');
+        end;
+    T:=P.Targets.AddUnit('libpcre2_16.pp');
+      with T.Dependencies do
+        begin
+          AddInclude('pcreconst.inc');
+        end;
+    T:=P.Targets.AddUnit('libpcre2_32.pp');
+    P.ExamplePath.Add('examples');
+    P.Targets.AddExampleProgram('tpcre.pp');
+    P.NamespaceMap:='namespaces.lst';
+
+{$ifndef ALLPACKAGES}
+    Run;
+    end;
+end.
+{$endif ALLPACKAGES}

+ 3 - 0
packages/libpcre/namespaced/Api.PCRE2_16.pp

@@ -0,0 +1,3 @@
+unit Api.PCRE2_16;
+{$DEFINE FPC_DOTTEDUNITS}
+{$i libpcre2_16.pp}

+ 3 - 0
packages/libpcre/namespaced/Api.PCRE2_32.pp

@@ -0,0 +1,3 @@
+unit Api.PCRE2_32;
+{$DEFINE FPC_DOTTEDUNITS}
+{$i libpcre2_32.pp}

+ 3 - 0
packages/libpcre/namespaced/Api.PCRE2_8.pp

@@ -0,0 +1,3 @@
+unit Api.PCRE2_8;
+{$DEFINE FPC_DOTTEDUNITS}
+{$i libpcre2_8.pp}

+ 5 - 0
packages/libpcre/namespaces.lst

@@ -0,0 +1,5 @@
+src/libpcre2_8.pp=namespaced/Api.PCRE2_8.pp
+src/libpcre2_16.pp=namespaced/Api.PCRE2_16.pp
+src/libpcre2_32.pp=namespaced/Api.PCRE2_32.pp
+{s*:src/}=namespaced/
+{i+:src/}

+ 530 - 0
packages/libpcre/src/libpcre2_16.pp

@@ -0,0 +1,530 @@
+{$mode objfpc}
+{$h+}
+{$IFNDEF FPC_DOTTEDUNITS}
+unit libpcre2_16;
+{$ENDIF}
+
+interface
+
+uses
+{$IFDEF FPC_DOTTEDUNITS}
+  System.CTypes;
+{$ELSE}
+  ctypes;
+{$ENDIF}
+
+const
+  {$IFDEF LINUX}
+    pcrelibname = 'libpcre2-16.so.0';
+  {$ELSE}
+    {$IFDEF windows}
+      pcrelibname = 'libpcre16-0.dll'; // As used in Mingw64
+    {$ELSE}
+      {$ERROR: platform not supported by pcre}
+    {$ENDIF}
+  {$ENDIF}
+
+{$i pcreconsts.inc}
+
+{
+  Automatically converted by H2Pas 1.0.0 from pre_pcre_8.h
+  The following command line parameters were used:
+    -c
+    -l
+    libpcre2-8
+    pre_pcre_8.h
+    -C
+    -o
+    libpcre28.pp
+    -P
+    -P
+    -t
+}
+
+{$IFDEF FPC}
+{$PACKRECORDS C}
+{$ENDIF}
+
+Type
+  tsize_t = csize_t;
+  PCRE2_SIZE = tsize_t;
+  PTsize_t = ^Tsize_t;
+  PPTsize_t = ^PTsize_t;
+  tuint32_t = cardinal;
+  Tint32_t = cuint32;
+  Tcint = cint;
+
+  TPCRE2_UCHAR8 = ansichar;
+  TPCRE2_SPTR8 = PAnsichar;
+  PTPCRE2_UCHAR8 = ^TPCRE2_UCHAR8;
+  PCRE2_SPTR8 = TPCRE2_SPTR8;
+  PTPCRE2_SPTR8 = PCRE2_SPTR8;
+  PPTPCRE2_UCHAR8 = ^PTPCRE2_UCHAR8;
+  PPPTPCRE2_UCHAR8 = ^PPTPCRE2_UCHAR8;
+
+  Ppcre2_callout_block_16  = ^Tpcre2_callout_block_16;
+  Ppcre2_callout_block = Ppcre2_callout_block_16;
+
+  Ppcre2_callout_enumerate_block_16  = ^Tpcre2_callout_enumerate_block_16;
+  Ppcre2_callout_enumerate_block = Ppcre2_callout_enumerate_block_16;
+
+  Ppcre2_code_16  = ^Tpcre2_code_16;
+  Ppcre2_code = Ppcre2_code_16;
+
+  Ppcre2_compile_context_16  = ^Tpcre2_compile_context_16;
+  Ppcre2_compile_context = Ppcre2_compile_context_16;
+
+  Ppcre2_convert_context_16  = ^Tpcre2_convert_context_16;
+  Ppcre2_convert_context = Ppcre2_convert_context_16;
+
+  Ppcre2_general_context_16  = ^Tpcre2_general_context_16;
+  Ppcre2_general_context = Ppcre2_general_context_16;
+
+  Ppcre2_jit_stack_16  = ^Tpcre2_jit_stack_16;
+  Ppcre2_jit_stack = Ppcre2_jit_stack_16;
+
+  Ppcre2_match_context_16  = ^Tpcre2_match_context_16;
+  Ppcre2_match_context = Ppcre2_match_context_16;
+
+  Ppcre2_match_data_16  = ^Tpcre2_match_data_16;
+  Ppcre2_match_data = Ppcre2_match_data_16;
+
+  TPCRE2_UCHAR16 = widechar;
+  PPCRE2_SPTR8  = ^TPCRE2_SPTR8;
+  Ppcre2_substitute_callout_block_16  = ^Tpcre2_substitute_callout_block_16;
+  PPCRE2_UCHAR8  = ^TPCRE2_UCHAR8;
+  PPCRE2_UCHAR16  = ^TPCRE2_UCHAR16;
+
+  Psize_t  = ^tsize_t;
+  Puint8_t  = ^byte;
+  PTuint8_t = Puint8_t;
+  PPTuint8_t = ^PTuint8_t;
+
+  TPCRE2_SPTR16 = ^TPCRE2_UCHAR16;
+  TPCRE2_SPTR = TPCRE2_SPTR16;
+
+  PTPCRE2_UCHAR16 = ^TPCRE2_UCHAR16;
+  PTPCRE2_UCHAR = PTPCRE2_UCHAR16;
+
+  PCRE2_SPTR16 = TPCRE2_SPTR16;
+  PCRE2_SPTR = PCRE2_SPTR16;
+
+  PTPCRE2_SPTR16 = PCRE2_SPTR16;
+  PTPCRE2_SPTR = PTPCRE2_SPTR16;
+
+  PPTPCRE2_UCHAR16 = ^PTPCRE2_UCHAR16;
+  PPTPCRE2_UCHAR = PPTPCRE2_UCHAR16;
+
+  PPPTPCRE2_UCHAR16 = ^PPTPCRE2_UCHAR16;
+  PPPTPCRE2_UCHAR = PPPTPCRE2_UCHAR16;
+
+  Tpcre2_real_general_context_16 = record
+  end;
+  Tpcre2_general_context_16 =  Tpcre2_real_general_context_16;
+  Tpcre2_general_context = Tpcre2_general_context_16;
+
+  Ppcre2_real_general_context_16 = ^tpcre2_real_general_context_16;
+  PTpcre2_general_context_16 = Ppcre2_real_general_context_16;
+
+  Tpcre2_real_compile_context_16 = record
+  end;
+  Tpcre2_compile_context_16 = Tpcre2_real_compile_context_16;
+  Tpcre2_compile_context = Tpcre2_compile_context_16;
+
+  Ppcre2_real_compile_context_16 = ^Tpcre2_real_compile_context_16;
+  PTpcre2_compile_context_16 = Ppcre2_real_compile_context_16;
+
+  Tpcre2_real_match_context_16 = record
+  end;
+  Tpcre2_match_context_16 = Tpcre2_real_match_context_16;
+  Tpcre2_match_context = Tpcre2_match_context_16;
+
+  Ppcre2_real_match_context_16 = ^Tpcre2_real_match_context_16;
+  PTpcre2_match_context_16 = Ppcre2_real_match_context_16;
+
+  Tpcre2_real_convert_context_16 = record
+  end;
+  Tpcre2_convert_context_16 = Tpcre2_real_convert_context_16;
+  Tpcre2_convert_context = Tpcre2_convert_context_16;
+
+  Ppcre2_real_convert_context_16 = ^Tpcre2_real_convert_context_16;
+  PTpcre2_convert_context_16 = Ppcre2_real_convert_context_16;
+
+  Tpcre2_real_code_16 = record
+  end;
+  Tpcre2_code_16 = Tpcre2_real_code_16;
+  Tpcre2_code = Tpcre2_code_16;
+
+  Ppcre2_real_code_16 = ^Tpcre2_real_code_16;
+  PTpcre2_code_16  = Ppcre2_real_code_16;
+  PPTpcre2_code_16 = ^PTpcre2_code_16;
+
+
+  Tpcre2_real_match_data_16 = record
+  end;
+  Tpcre2_match_data_16 = Tpcre2_real_match_data_16;
+  Tpcre2_match_data = Tpcre2_match_data_16;
+
+  Ppcre2_real_match_data_16 = ^Tpcre2_real_match_data_16;
+  PTpcre2_match_data_16 = Ppcre2_real_match_data_16;
+
+
+
+  Tpcre2_real_jit_stack_16 = record
+  end;
+  Tpcre2_jit_stack_16 = Tpcre2_real_jit_stack_16;
+  Tpcre2_jit_stack = Tpcre2_jit_stack_16;
+  
+  Ppcre2_real_jit_stack_16 = ^Tpcre2_real_jit_stack_16;
+  PTpcre2_jit_stack_16 = Ppcre2_real_jit_stack_16;
+
+
+  Tpcre2_jit_callback_16 = function (_para1:pointer): PTpcre2_jit_stack_16;cdecl;
+
+  Tpcre2_callout_block_16 = record
+    version : Tuint32_t;
+    callout_number : Tuint32_t;
+    capture_top : Tuint32_t;
+    capture_last : Tuint32_t;
+    offset_vector : ^Tsize_t;
+    mark : TPCRE2_SPTR8;
+    subject : TPCRE2_SPTR8;
+    subject_length : Tsize_t;
+    start_match : Tsize_t;
+    current_position : Tsize_t;
+    pattern_position : Tsize_t;
+    next_item_length : Tsize_t;
+    callout_string_offset : Tsize_t;
+    callout_string_length : Tsize_t;
+    callout_string : TPCRE2_SPTR8;
+    callout_flags : Tuint32_t;
+  end;
+
+
+  Tpcre2_callout_enumerate_block_16 = record
+    version : Tuint32_t;
+    pattern_position : Tsize_t;
+    next_item_length : Tsize_t;
+    callout_number : Tuint32_t;
+    callout_string_offset : Tsize_t;
+    callout_string_length : Tsize_t;
+    callout_string : TPCRE2_SPTR8;
+  end;
+  PTpcre2_callout_enumerate_block_16 = ^Tpcre2_callout_enumerate_block_16;
+
+  Tpcre2_substitute_callout_block_16 = record
+    version : Tuint32_t;
+    input : TPCRE2_SPTR8;
+    output : TPCRE2_SPTR8;
+    output_offsets : array[0..1] of Tsize_t;
+    ovector : ^Tsize_t;
+    oveccount : Tuint32_t;
+    subscount : Tuint32_t;
+
+  end;
+  PTpcre2_substitute_callout_block_16 = ^  Tpcre2_substitute_callout_block_16;
+
+  tpcre2_malloc = function (_para1:Tsize_t; _para2:pointer) : Pointer; cdecl;
+  tpcre2_free = procedure (_para1:pointer; _para2:pointer); cdecl;
+  tpcre2_set_compile_recursion_guard_16_callback = function (_para1:Tuint32_t; _para2:pointer):Tcint; cdecl;
+  tpcre2_set_callout_16_callback = function (_para1:Ppcre2_callout_block_16; _para2:pointer):Tcint; cdecl;
+  tpcre2_callout_enumerate_16_callback = function (_para1: PTpcre2_callout_enumerate_block_16; _para2:pointer):Tcint; cdecl;
+  tpcre2_set_substitute_callout_16_callback =   function (_para1:Ppcre2_substitute_callout_block_16; _para2:pointer):Tcint; cdecl;
+     
+var
+  pcre2_config : function(_para1:Tuint32_t; _para2:pointer):Tcint;cdecl;
+  pcre2_general_context_copy : function(_para1:PTpcre2_general_context_16): PTpcre2_general_context_16;cdecl;
+  pcre2_general_context_create : function(_para1:tpcre2_malloc; _para2:tpcre2_free; _para3:pointer):PTpcre2_general_context_16;cdecl;
+  pcre2_general_context_free : procedure(_para1:PTpcre2_general_context_16);cdecl;
+  pcre2_compile_context_copy : function(_para1:PTpcre2_compile_context_16):PTpcre2_compile_context_16;cdecl;
+  pcre2_compile_context_create : function(_para1:PTpcre2_general_context_16):PTpcre2_compile_context_16;cdecl;
+  pcre2_compile_context_free : procedure(_para1:PTpcre2_compile_context_16);cdecl;
+  pcre2_set_bsr : function(_para1:PTpcre2_compile_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_character_tables : function(_para1:PTpcre2_compile_context_16; _para2: Puint8_t):Tcint;cdecl;
+  pcre2_set_compile_extra_options : function(_para1:PTpcre2_compile_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_max_pattern_length : function(_para1:PTpcre2_compile_context_16; _para2:Tsize_t):Tcint;cdecl;
+  pcre2_set_newline : function(_para1:PTpcre2_compile_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_parens_nest_limit : function(_para1:PTpcre2_compile_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_compile_recursion_guard : function(_para1:PTpcre2_compile_context_16; _para2: tpcre2_set_compile_recursion_guard_16_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_convert_context_copy : function(_para1:PTpcre2_convert_context_16):PTpcre2_convert_context_16;cdecl;
+  pcre2_convert_context_create : function(_para1:PTpcre2_general_context_16):PTpcre2_convert_context_16;cdecl;
+  pcre2_convert_context_free : procedure(_para1:PTpcre2_convert_context_16);cdecl;
+  pcre2_set_glob_escape : function(_para1:PTpcre2_convert_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_glob_separator : function(_para1:PTpcre2_convert_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_pattern_convert : function(_para1:TPCRE2_SPTR8; _para2:Tsize_t; _para3:Tuint32_t; _para4:PPTPCRE2_UCHAR8; _para5: Psize_t;  _para6:PTpcre2_convert_context_16):Tcint;cdecl;
+  pcre2_converted_pattern_free : procedure(_para1:PTPCRE2_UCHAR8);cdecl;
+  pcre2_match_context_copy : function(_para1:PTpcre2_match_context_16):PTpcre2_match_context_16;cdecl;
+  pcre2_match_context_create : function(_para1:PTpcre2_general_context_16):PTpcre2_match_context_16;cdecl;
+  pcre2_match_context_free : procedure(_para1:PTpcre2_match_context_16);cdecl;
+  pcre2_set_callout : function(_para1:PTpcre2_match_context_16; _para2: tpcre2_set_callout_16_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_set_substitute_callout : function(_para1:PTpcre2_match_context_16; _para2:tpcre2_set_substitute_callout_16_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_set_depth_limit : function(_para1:PTpcre2_match_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_heap_limit : function(_para1:PTpcre2_match_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_match_limit : function(_para1:PTpcre2_match_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_offset_limit : function(_para1:PTpcre2_match_context_16; _para2:Tsize_t):Tcint;cdecl;
+  pcre2_set_recursion_limit : function(_para1:PTpcre2_match_context_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_recursion_memory_management : function(_para1:PTpcre2_match_context_16; _para2: tpcre2_malloc; _para3:tpcre2_free; _para4:pointer):Tcint;cdecl;
+  pcre2_compile : function(_para1:TPCRE2_SPTR8; _para2:Tsize_t; _para3:Tuint32_t; _para4:Pcint; _para5:Psize_t; _para6:PTpcre2_compile_context_16):Ppcre2_code_16;cdecl;
+  // PCRE actually uses TPCRE2_SPTR8. With this we avoid a typecast
+  pcre2_compile_w : function(_para1:TPCRE2_SPTR16; _para2:Tsize_t; _para3:Tuint32_t; _para4:Pcint; _para5:Psize_t; _para6:PTpcre2_compile_context_16):Ppcre2_code_16;cdecl;
+  pcre2_code_free : procedure(_para1:PTpcre2_code_16);cdecl;
+  pcre2_code_copy : function(_para1:PTpcre2_code_16):PTpcre2_code_16;cdecl;
+  pcre2_code_copy_with_tables : function(_para1:PTpcre2_code_16):PTpcre2_code_16;cdecl;
+  pcre2_pattern_info : function(_para1:PTpcre2_code_16; _para2:Tuint32_t; _para3:pointer):Tcint;cdecl;
+  pcre2_callout_enumerate : function(_para1:PTpcre2_code_16; _para2: tpcre2_callout_enumerate_16_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_match_data_create : function(_para1:Tuint32_t; _para2:PTpcre2_general_context_16):PTpcre2_match_data_16;cdecl;
+  pcre2_match_data_create_from_pattern : function(_para1:PTpcre2_code_16; _para2:PTpcre2_general_context_16):PTpcre2_match_data_16;cdecl;
+  pcre2_dfa_match : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_16; _para7:PTpcre2_match_context_16; _para8:Pcint; _para9:Tsize_t):Tcint;cdecl;
+  // PCRE actually uses TPCRE2_SPTR8. With this we avoid a typecast
+  pcre2_dfa_match_w : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR16; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_16; _para7:PTpcre2_match_context_16; _para8:Pcint; _para9:Tsize_t):Tcint;cdecl;
+  pcre2_match : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_16; _para7:PTpcre2_match_context_16):Tcint;cdecl;
+  // PCRE actually uses TPCRE2_SPTR8. With this we avoid a typecast
+  pcre2_match_w : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR16; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_16; _para7:PTpcre2_match_context_16):Tcint;cdecl;
+  pcre2_match_data_free : procedure(_para1:PTpcre2_match_data_16);cdecl;
+  pcre2_get_mark : function(_para1:PTpcre2_match_data_16):TPCRE2_SPTR8;cdecl;
+  pcre2_get_match_data_size : function(_para1:PTpcre2_match_data_16):Tsize_t;cdecl;
+  pcre2_get_ovector_count : function(_para1:PTpcre2_match_data_16):Tuint32_t;cdecl;
+  pcre2_get_ovector_pointer : function(_para1:PTpcre2_match_data_16):Psize_t;cdecl;
+  pcre2_get_startchar : function(_para1:PTpcre2_match_data_16):Tsize_t;cdecl;
+  pcre2_substring_copy_byname : function(_para1:PTpcre2_match_data_16; _para2:TPCRE2_SPTR8; _para3:PTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_copy_bynumber : function(_para1:PTpcre2_match_data_16; _para2:Tuint32_t; _para3:PTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_free : procedure(_para1:PTPCRE2_UCHAR8);cdecl;
+  pcre2_substring_get_byname : function(_para1:PTpcre2_match_data_16; _para2:TPCRE2_SPTR8; _para3:PPTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_get_bynumber : function(_para1:PTpcre2_match_data_16; _para2:Tuint32_t; _para3:PPTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_length_byname : function(_para1:PTpcre2_match_data_16; _para2:TPCRE2_SPTR8; _para3:PTsize_t):Tcint;cdecl;
+  pcre2_substring_length_bynumber : function(_para1:PTpcre2_match_data_16; _para2:Tuint32_t; _para3:PTsize_t):Tcint;cdecl;
+  pcre2_substring_nametable_scan : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR8; _para3:PTPCRE2_SPTR8; _para4:PTPCRE2_SPTR8):Tcint;cdecl;
+  pcre2_substring_number_from_name : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR8):Tcint;cdecl;
+  pcre2_substring_list_free : procedure(_para1:PTPCRE2_SPTR8);cdecl;
+  pcre2_substring_list_get : function(_para1:PTpcre2_match_data_16; _para2:PPPTPCRE2_UCHAR8; _para3:PPTsize_t):Tcint;cdecl;
+  pcre2_serialize_encode : function(_para1:PPTpcre2_code_16; _para2:Tint32_t; _para3:PPTuint8_t; _para4:PTsize_t; _para5:PTpcre2_general_context_16):Tint32_t;cdecl;
+  pcre2_serialize_decode : function(_para1:PPTpcre2_code_16; _para2:Tint32_t; _para3:PTuint8_t; _para4:PTpcre2_general_context_16):Tint32_t;cdecl;
+  pcre2_serialize_get_number_of_codes : function(_para1:PTuint8_t):Tint32_t;cdecl;
+  pcre2_serialize_free : procedure(_para1:PTuint8_t);cdecl;
+  pcre2_substitute : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_16; _para7:PTpcre2_match_context_16; _para8:TPCRE2_SPTR8; _para9:Tsize_t; _para10:PTPCRE2_UCHAR8;  _para11:PTsize_t):Tcint;cdecl;
+  pcre2_jit_compile : function(_para1:PTpcre2_code_16; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_jit_match : function(_para1:PTpcre2_code_16; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_16; _para7:PTpcre2_match_context_16):Tcint;cdecl;
+  pcre2_jit_free_unused_memory : procedure(_para1:PTpcre2_general_context_16);cdecl;
+  pcre2_jit_stack_create : function(_para1:Tsize_t; _para2:Tsize_t; _para3:PTpcre2_general_context_16):PTpcre2_jit_stack_16;cdecl;
+  pcre2_jit_stack_assign : procedure(_para1:PTpcre2_match_context_16; _para2:Tpcre2_jit_callback_16; _para3:pointer);cdecl;
+  pcre2_jit_stack_free : procedure(_para1:PTpcre2_jit_stack_16);cdecl;
+  pcre2_get_error_message : function(_para1:Tcint; _para2:PTPCRE2_UCHAR8; _para3:Tsize_t):Tcint;cdecl;
+  pcre2_maketables : function(_para1:PTpcre2_general_context_16):PTuint8_t;cdecl;
+  pcre2_maketables_free : procedure(_para1:PTpcre2_general_context_16; _para2:PTuint8_t);cdecl;
+
+function libpcre28loaded : Boolean;
+procedure Loadlibpcre28; overload;
+procedure Loadlibpcre28(const lib : string); overload;
+procedure Freelibpcre28;
+
+implementation
+
+uses
+{$IFDEF FPC_DOTTEDUNITS}
+  System.SysUtils, System.DynLibs;
+{$ELSE}
+  SysUtils, dynlibs;
+{$ENDIF}
+
+
+var
+  hlib : tlibhandle;
+
+
+function libpcre28loaded : Boolean;
+begin
+  Result:=(hLib<>NilHandle);
+end;
+
+procedure Freelibpcre28;
+
+begin
+  if hlib=nilhandle then exit;
+  FreeLibrary(hlib);
+  hlib:=NilHandle;
+  pcre2_config:=nil;
+  pcre2_general_context_copy:=nil;
+  pcre2_general_context_create:=nil;
+  pcre2_general_context_free:=nil;
+  pcre2_compile_context_copy:=nil;
+  pcre2_compile_context_create:=nil;
+  pcre2_compile_context_free:=nil;
+  pcre2_set_bsr:=nil;
+  pcre2_set_character_tables:=nil;
+  pcre2_set_compile_extra_options:=nil;
+  pcre2_set_max_pattern_length:=nil;
+  pcre2_set_newline:=nil;
+  pcre2_set_parens_nest_limit:=nil;
+  pcre2_set_compile_recursion_guard:=nil;
+  pcre2_convert_context_copy:=nil;
+  pcre2_convert_context_create:=nil;
+  pcre2_convert_context_free:=nil;
+  pcre2_set_glob_escape:=nil;
+  pcre2_set_glob_separator:=nil;
+  pcre2_pattern_convert:=nil;
+  pcre2_converted_pattern_free:=nil;
+  pcre2_match_context_copy:=nil;
+  pcre2_match_context_create:=nil;
+  pcre2_match_context_free:=nil;
+  pcre2_set_callout:=nil;
+  pcre2_set_substitute_callout:=nil;
+  pcre2_set_depth_limit:=nil;
+  pcre2_set_heap_limit:=nil;
+  pcre2_set_match_limit:=nil;
+  pcre2_set_offset_limit:=nil;
+  pcre2_set_recursion_limit:=nil;
+  pcre2_set_recursion_memory_management:=nil;
+  pcre2_compile:=nil;
+  pcre2_compile_w:=Nil;
+  pcre2_code_free:=nil;
+  pcre2_code_copy:=nil;
+  pcre2_code_copy_with_tables:=nil;
+  pcre2_pattern_info:=nil;
+  pcre2_callout_enumerate:=nil;
+  pcre2_match_data_create:=nil;
+  pcre2_match_data_create_from_pattern:=nil;
+  pcre2_dfa_match:=nil;
+  pcre2_dfa_match_w:=nil;
+  pcre2_match:=nil;
+  pcre2_match_w:=nil;
+  pcre2_match_data_free:=nil;
+  pcre2_get_mark:=nil;
+  pcre2_get_match_data_size:=nil;
+  pcre2_get_ovector_count:=nil;
+  pcre2_get_ovector_pointer:=nil;
+  pcre2_get_startchar:=nil;
+  pcre2_substring_copy_byname:=nil;
+  pcre2_substring_copy_bynumber:=nil;
+  pcre2_substring_free:=nil;
+  pcre2_substring_get_byname:=nil;
+  pcre2_substring_get_bynumber:=nil;
+  pcre2_substring_length_byname:=nil;
+  pcre2_substring_length_bynumber:=nil;
+  pcre2_substring_nametable_scan:=nil;
+  pcre2_substring_number_from_name:=nil;
+  pcre2_substring_list_free:=nil;
+  pcre2_substring_list_get:=nil;
+  pcre2_serialize_encode:=nil;
+  pcre2_serialize_decode:=nil;
+  pcre2_serialize_get_number_of_codes:=nil;
+  pcre2_serialize_free:=nil;
+  pcre2_substitute:=nil;
+  pcre2_jit_compile:=nil;
+  pcre2_jit_match:=nil;
+  pcre2_jit_free_unused_memory:=nil;
+  pcre2_jit_stack_create:=nil;
+  pcre2_jit_stack_assign:=nil;
+  pcre2_jit_stack_free:=nil;
+  pcre2_get_error_message:=nil;
+  pcre2_maketables:=nil;
+  pcre2_maketables_free:=nil;
+end;
+
+
+procedure Loadlibpcre28;
+begin
+  Loadlibpcre28(pcrelibname);
+end;
+
+
+procedure Loadlibpcre28(const lib : string);
+
+  Function GetAddr(const aName : string) : Pointer;
+
+  begin
+    Result:=GetProcAddress(hlib,aname);
+    if Result=Nil then
+      if IsConsole then
+        Writeln(stdErr,'Could not load procedure: ',aName)
+  end;
+
+begin
+  Freelibpcre28;
+  hlib:=LoadLibrary(lib);
+  if (hlib=NilHandle) then
+    raise Exception.Create(format('Could not load library: %s',[lib]));
+  pointer(pcre2_config):=GetAddr('pcre2_config_16');
+  pointer(pcre2_general_context_copy):=GetAddr('pcre2_general_context_copy_16');
+  pointer(pcre2_general_context_create):=GetAddr('pcre2_general_context_create_16');
+  pointer(pcre2_general_context_free):=GetAddr('pcre2_general_context_free_16');
+  pointer(pcre2_compile_context_copy):=GetAddr('pcre2_compile_context_copy_16');
+  pointer(pcre2_compile_context_create):=GetAddr('pcre2_compile_context_create_16');
+  pointer(pcre2_compile_context_free):=GetAddr('pcre2_compile_context_free_16');
+  pointer(pcre2_set_bsr):=GetAddr('pcre2_set_bsr_16');
+  pointer(pcre2_set_character_tables):=GetAddr('pcre2_set_character_tables_16');
+  pointer(pcre2_set_compile_extra_options):=GetAddr('pcre2_set_compile_extra_options_16');
+  pointer(pcre2_set_max_pattern_length):=GetAddr('pcre2_set_max_pattern_length_16');
+  pointer(pcre2_set_newline):=GetAddr('pcre2_set_newline_16');
+  pointer(pcre2_set_parens_nest_limit):=GetAddr('pcre2_set_parens_nest_limit_16');
+  pointer(pcre2_set_compile_recursion_guard):=GetAddr('pcre2_set_compile_recursion_guard_16');
+  pointer(pcre2_convert_context_copy):=GetAddr('pcre2_convert_context_copy_16');
+  pointer(pcre2_convert_context_create):=GetAddr('pcre2_convert_context_create_16');
+  pointer(pcre2_convert_context_free):=GetAddr('pcre2_convert_context_free_16');
+  pointer(pcre2_set_glob_escape):=GetAddr('pcre2_set_glob_escape_16');
+  pointer(pcre2_set_glob_separator):=GetAddr('pcre2_set_glob_separator_16');
+  pointer(pcre2_pattern_convert):=GetAddr('pcre2_pattern_convert_16');
+  pointer(pcre2_converted_pattern_free):=GetAddr('pcre2_converted_pattern_free_16');
+  pointer(pcre2_match_context_copy):=GetAddr('pcre2_match_context_copy_16');
+  pointer(pcre2_match_context_create):=GetAddr('pcre2_match_context_create_16');
+  pointer(pcre2_match_context_free):=GetAddr('pcre2_match_context_free_16');
+  pointer(pcre2_set_callout):=GetAddr('pcre2_set_callout_16');
+  pointer(pcre2_set_substitute_callout):=GetAddr('pcre2_set_substitute_callout_16');
+  pointer(pcre2_set_depth_limit):=GetAddr('pcre2_set_depth_limit_16');
+  pointer(pcre2_set_heap_limit):=GetAddr('pcre2_set_heap_limit_16');
+  pointer(pcre2_set_match_limit):=GetAddr('pcre2_set_match_limit_16');
+  pointer(pcre2_set_offset_limit):=GetAddr('pcre2_set_offset_limit_16');
+  pointer(pcre2_set_recursion_limit):=GetAddr('pcre2_set_recursion_limit_16');
+  pointer(pcre2_set_recursion_memory_management):=GetAddr('pcre2_set_recursion_memory_management_16');
+  pointer(pcre2_compile):=GetAddr('pcre2_compile_16');
+  pointer(pcre2_compile_w):=GetAddr('pcre2_compile_16');
+  pointer(pcre2_code_free):=GetAddr('pcre2_code_free_16');
+  pointer(pcre2_code_copy):=GetAddr('pcre2_code_copy_16');
+  pointer(pcre2_code_copy_with_tables):=GetAddr('pcre2_code_copy_with_tables_16');
+  pointer(pcre2_pattern_info):=GetAddr('pcre2_pattern_info_16');
+  pointer(pcre2_callout_enumerate):=GetAddr('pcre2_callout_enumerate_16');
+  pointer(pcre2_match_data_create):=GetAddr('pcre2_match_data_create_16');
+  pointer(pcre2_match_data_create_from_pattern):=GetAddr('pcre2_match_data_create_from_pattern_16');
+  pointer(pcre2_dfa_match):=GetAddr('pcre2_dfa_match_16');
+  pointer(pcre2_dfa_match_w):=GetAddr('pcre2_dfa_match_16');
+  pointer(pcre2_match):=GetAddr('pcre2_match_16');
+  pointer(pcre2_match_w):=GetAddr('pcre2_match_16');
+  pointer(pcre2_match_data_free):=GetAddr('pcre2_match_data_free_16');
+  pointer(pcre2_get_mark):=GetAddr('pcre2_get_mark_16');
+  pointer(pcre2_get_match_data_size):=GetAddr('pcre2_get_match_data_size_16');
+  pointer(pcre2_get_ovector_count):=GetAddr('pcre2_get_ovector_count_16');
+  pointer(pcre2_get_ovector_pointer):=GetAddr('pcre2_get_ovector_pointer_16');
+  pointer(pcre2_get_startchar):=GetAddr('pcre2_get_startchar_16');
+  pointer(pcre2_substring_copy_byname):=GetAddr('pcre2_substring_copy_byname_16');
+  pointer(pcre2_substring_copy_bynumber):=GetAddr('pcre2_substring_copy_bynumber_16');
+  pointer(pcre2_substring_free):=GetAddr('pcre2_substring_free_16');
+  pointer(pcre2_substring_get_byname):=GetAddr('pcre2_substring_get_byname_16');
+  pointer(pcre2_substring_get_bynumber):=GetAddr('pcre2_substring_get_bynumber_16');
+  pointer(pcre2_substring_length_byname):=GetAddr('pcre2_substring_length_byname_16');
+  pointer(pcre2_substring_length_bynumber):=GetAddr('pcre2_substring_length_bynumber_16');
+  pointer(pcre2_substring_nametable_scan):=GetAddr('pcre2_substring_nametable_scan_16');
+  pointer(pcre2_substring_number_from_name):=GetAddr('pcre2_substring_number_from_name_16');
+  pointer(pcre2_substring_list_free):=GetAddr('pcre2_substring_list_free_16');
+  pointer(pcre2_substring_list_get):=GetAddr('pcre2_substring_list_get_16');
+  pointer(pcre2_serialize_encode):=GetAddr('pcre2_serialize_encode_16');
+  pointer(pcre2_serialize_decode):=GetAddr('pcre2_serialize_decode_16');
+  pointer(pcre2_serialize_get_number_of_codes):=GetAddr('pcre2_serialize_get_number_of_codes_16');
+  pointer(pcre2_serialize_free):=GetAddr('pcre2_serialize_free_16');
+  pointer(pcre2_substitute):=GetAddr('pcre2_substitute_16');
+  pointer(pcre2_jit_compile):=GetAddr('pcre2_jit_compile_16');
+  pointer(pcre2_jit_match):=GetAddr('pcre2_jit_match_16');
+  pointer(pcre2_jit_free_unused_memory):=GetAddr('pcre2_jit_free_unused_memory_16');
+  pointer(pcre2_jit_stack_create):=GetAddr('pcre2_jit_stack_create_16');
+  pointer(pcre2_jit_stack_assign):=GetAddr('pcre2_jit_stack_assign_16');
+  pointer(pcre2_jit_stack_free):=GetAddr('pcre2_jit_stack_free_16');
+  pointer(pcre2_get_error_message):=GetAddr('pcre2_get_error_message_16');
+  pointer(pcre2_maketables):=GetAddr('pcre2_maketables_16');
+  pointer(pcre2_maketables_free):=GetAddr('pcre2_maketables_free_16');
+end;
+
+
+initialization
+  Loadlibpcre28;
+finalization
+  Freelibpcre28;
+
+end.

+ 493 - 0
packages/libpcre/src/libpcre2_32.pp

@@ -0,0 +1,493 @@
+{$mode objfpc}
+{$h+}
+{$IFNDEF FPC_DOTTEDUNITS}
+unit libpcre2_32;
+{$ENDIF}
+
+interface
+
+uses
+{$IFDEF FPC_DOTTEDUNITS}
+  System.CTypes;
+{$ELSE}
+  ctypes;
+{$ENDIF}
+
+const
+{$IFDEF LINUX}
+  pcrelibname = 'libpcre2-32.so.0';
+{$ELSE}
+  {$IFDEF windows}
+    pcrelibname = 'libpcre32-0.dll'; // As used in Mingw64
+  {$ELSE}
+    {$ERROR: platform not supported by pcre}
+  {$ENDIF}
+{$ENDIF}
+
+
+{$i pcreconsts.inc}
+
+{
+  Automatically converted by H2Pas 1.0.0 from pre_pcre_32.h
+  The following command line parameters were used:
+    -c
+    -l
+    libpcre2-8
+    pre_pcre_32.h
+    -C
+    -o
+    libpcre28.pp
+    -P
+    -P
+    -t
+}
+
+{$IFDEF FPC}
+{$PACKRECORDS C}
+{$ENDIF}
+
+Type
+  tsize_t = csize_t;
+  PCRE2_SIZE = tsize_t;
+  PTsize_t = ^Tsize_t;
+  PPTsize_t = ^PTsize_t;
+  tuint32_t = cardinal;
+  Tint32_t = cuint32;
+  Tcint = cint;
+
+  TPCRE2_UCHAR8 = ansichar;
+  TPCRE2_SPTR8 = PAnsichar;
+  PTPCRE2_UCHAR8 = ^TPCRE2_UCHAR8;
+  PCRE2_SPTR8 = TPCRE2_SPTR8;
+  PTPCRE2_SPTR8 = PCRE2_SPTR8;
+  PPTPCRE2_UCHAR8 = ^PTPCRE2_UCHAR8;
+  PPPTPCRE2_UCHAR8 = ^PPTPCRE2_UCHAR8;
+
+  Ppcre2_callout_block_32  = ^Tpcre2_callout_block_32;
+  Ppcre2_callout_block = Ppcre2_callout_block_32;
+
+  Ppcre2_callout_enumerate_block_32  = ^Tpcre2_callout_enumerate_block_32;
+  Ppcre2_callout_enumerate_block = Ppcre2_callout_enumerate_block_32;
+
+  Ppcre2_code_32  = ^Tpcre2_code_32;
+  Ppcre2_code = Ppcre2_code_32;
+
+  Ppcre2_compile_context_32  = ^Tpcre2_compile_context_32;
+  Ppcre2_compile_context = Ppcre2_compile_context_32;
+
+  Ppcre2_convert_context_32  = ^Tpcre2_convert_context_32;
+  Ppcre2_convert_context = Ppcre2_convert_context_32;
+
+  Ppcre2_general_context_32  = ^Tpcre2_general_context_32;
+  Ppcre2_general_context = Ppcre2_general_context_32;
+
+  Ppcre2_jit_stack_32  = ^Tpcre2_jit_stack_32;
+  Ppcre2_jit_stack = Ppcre2_jit_stack_32;
+
+  Ppcre2_match_context_32  = ^Tpcre2_match_context_32;
+  Ppcre2_match_context = Ppcre2_match_context_32;
+
+  Ppcre2_match_data_32  = ^Tpcre2_match_data_32;
+  Ppcre2_match_data = Ppcre2_match_data_32;
+
+  Psize_t  = ^tsize_t;
+  Puint8_t  = ^byte;
+  PTuint8_t = Puint8_t;
+  PPTuint8_t = ^PTuint8_t;
+
+  Tpcre2_real_general_context_32 = record
+  end;
+  Tpcre2_general_context_32 = Tpcre2_real_general_context_32;
+  Tpcre2_general_context = Tpcre2_general_context_32;
+
+  Ppcre2_real_general_context_32 = ^tpcre2_real_general_context_32;
+  PTpcre2_general_context_32 = Ppcre2_real_general_context_32;
+  
+  Tpcre2_real_compile_context_32 = record
+  end;
+  Tpcre2_compile_context_32 = Tpcre2_real_compile_context_32;
+  Tpcre2_compile_context = Tpcre2_compile_context_32;
+  
+  Ppcre2_real_compile_context_32 = ^Tpcre2_real_compile_context_32;
+  PTpcre2_compile_context_32 = Ppcre2_real_compile_context_32;
+  
+  Tpcre2_real_match_context_32 = record
+  end;
+  Tpcre2_match_context_32 = Tpcre2_real_match_context_32;
+  Tpcre2_match_context = Tpcre2_match_context_32;
+  
+  Ppcre2_real_match_context_32 = ^Tpcre2_real_match_context_32;
+  PTpcre2_match_context_32 = Ppcre2_real_match_context_32;
+
+  Tpcre2_real_convert_context_32 = record
+  end;
+  Tpcre2_convert_context_32 = Tpcre2_real_convert_context_32;
+  Tpcre2_convert_context = Tpcre2_convert_context_32;
+
+  Ppcre2_real_convert_context_32 = ^Tpcre2_real_convert_context_32;
+  PTpcre2_convert_context_32 = Ppcre2_real_convert_context_32;
+
+  Tpcre2_real_code_32 = record
+  end;
+  Tpcre2_code_32 = Tpcre2_real_code_32;
+  Tpcre2_code = Tpcre2_code_32;
+
+  Ppcre2_real_code_32 = ^Tpcre2_real_code_32;
+  PTpcre2_code_32  = Ppcre2_real_code_32;
+  PPTpcre2_code_32 = ^PTpcre2_code_32;
+
+
+  Tpcre2_real_match_data_32 = record
+  end;
+  Tpcre2_match_data_32 = Tpcre2_real_match_data_32;
+  Tpcre2_match_data = Tpcre2_match_data_32;
+  
+  Ppcre2_real_match_data_32 = ^Tpcre2_real_match_data_32;
+  PTpcre2_match_data_32 = Ppcre2_real_match_data_32;
+
+  Tpcre2_real_jit_stack_32 = record
+  end;
+  Tpcre2_jit_stack_32 = Tpcre2_real_jit_stack_32;
+  Tpcre2_jit_stack = Tpcre2_jit_stack_32;
+  Ppcre2_real_jit_stack_32 = ^Tpcre2_real_jit_stack_32;
+  PTpcre2_jit_stack_32 = Ppcre2_real_jit_stack_32;
+
+  Tpcre2_jit_callback_32 = function (_para1:pointer): PTpcre2_jit_stack_32;cdecl;
+
+  Tpcre2_callout_block_32 = record
+    version : Tuint32_t;
+    callout_number : Tuint32_t;
+    capture_top : Tuint32_t;
+    capture_last : Tuint32_t;
+    offset_vector : ^Tsize_t;
+    mark : TPCRE2_SPTR8;
+    subject : TPCRE2_SPTR8;
+    subject_length : Tsize_t;
+    start_match : Tsize_t;
+    current_position : Tsize_t;
+    pattern_position : Tsize_t;
+    next_item_length : Tsize_t;
+    callout_string_offset : Tsize_t;
+    callout_string_length : Tsize_t;
+    callout_string : TPCRE2_SPTR8;
+    callout_flags : Tuint32_t;
+  end;
+
+
+  Tpcre2_callout_enumerate_block_32 = record
+    version : Tuint32_t;
+    pattern_position : Tsize_t;
+    next_item_length : Tsize_t;
+    callout_number : Tuint32_t;
+    callout_string_offset : Tsize_t;
+    callout_string_length : Tsize_t;
+    callout_string : TPCRE2_SPTR8;
+  end;
+  PTpcre2_callout_enumerate_block_32 = ^Tpcre2_callout_enumerate_block_32;
+
+  Tpcre2_substitute_callout_block_32 = record
+    version : Tuint32_t;
+    input : TPCRE2_SPTR8;
+    output : TPCRE2_SPTR8;
+    output_offsets : array[0..1] of Tsize_t;
+    ovector : ^Tsize_t;
+    oveccount : Tuint32_t;
+    subscount : Tuint32_t;
+
+  end;
+  PTpcre2_substitute_callout_block_32 = ^  Tpcre2_substitute_callout_block_32;
+  Ppcre2_substitute_callout_block_32 = PTpcre2_substitute_callout_block_32;
+
+  tpcre2_malloc = function (_para1:Tsize_t; _para2:pointer) : Pointer; cdecl;
+  tpcre2_free = procedure (_para1:pointer; _para2:pointer); cdecl;
+  tpcre2_set_compile_recursion_guard_32_callback = function (_para1:Tuint32_t; _para2:pointer):Tcint; cdecl;
+  tpcre2_set_callout_32_callback = function (_para1:Ppcre2_callout_block_32; _para2:pointer):Tcint; cdecl;
+  tpcre2_callout_enumerate_32_callback = function (_para1: PTpcre2_callout_enumerate_block_32; _para2:pointer):Tcint; cdecl;
+  tpcre2_set_substitute_callout_32_callback =   function (_para1:Ppcre2_substitute_callout_block_32; _para2:pointer):Tcint; cdecl;
+     
+var
+  pcre2_config : function(_para1:Tuint32_t; _para2:pointer):Tcint;cdecl;
+  pcre2_general_context_copy : function(_para1:PTpcre2_general_context_32): PTpcre2_general_context_32;cdecl;
+  pcre2_general_context_create : function(_para1:tpcre2_malloc; _para2:tpcre2_free; _para3:pointer):PTpcre2_general_context_32;cdecl;
+  pcre2_general_context_free : procedure(_para1:PTpcre2_general_context_32);cdecl;
+  pcre2_compile_context_copy : function(_para1:PTpcre2_compile_context_32):PTpcre2_compile_context_32;cdecl;
+  pcre2_compile_context_create : function(_para1:PTpcre2_general_context_32):PTpcre2_compile_context_32;cdecl;
+  pcre2_compile_context_free : procedure(_para1:PTpcre2_compile_context_32);cdecl;
+  pcre2_set_bsr : function(_para1:PTpcre2_compile_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_character_tables : function(_para1:PTpcre2_compile_context_32; _para2: Puint8_t):Tcint;cdecl;
+  pcre2_set_compile_extra_options : function(_para1:PTpcre2_compile_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_max_pattern_length : function(_para1:PTpcre2_compile_context_32; _para2:Tsize_t):Tcint;cdecl;
+  pcre2_set_newline : function(_para1:PTpcre2_compile_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_parens_nest_limit : function(_para1:PTpcre2_compile_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_compile_recursion_guard : function(_para1:PTpcre2_compile_context_32; _para2: tpcre2_set_compile_recursion_guard_32_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_convert_context_copy : function(_para1:PTpcre2_convert_context_32):PTpcre2_convert_context_32;cdecl;
+  pcre2_convert_context_create : function(_para1:PTpcre2_general_context_32):PTpcre2_convert_context_32;cdecl;
+  pcre2_convert_context_free : procedure(_para1:PTpcre2_convert_context_32);cdecl;
+  pcre2_set_glob_escape : function(_para1:PTpcre2_convert_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_glob_separator : function(_para1:PTpcre2_convert_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_pattern_convert : function(_para1:TPCRE2_SPTR8; _para2:Tsize_t; _para3:Tuint32_t; _para4:PPTPCRE2_UCHAR8; _para5: Psize_t;  _para6:PTpcre2_convert_context_32):Tcint;cdecl;
+  pcre2_converted_pattern_free : procedure(_para1:PTPCRE2_UCHAR8);cdecl;
+  pcre2_match_context_copy : function(_para1:PTpcre2_match_context_32):PTpcre2_match_context_32;cdecl;
+  pcre2_match_context_create : function(_para1:PTpcre2_general_context_32):PTpcre2_match_context_32;cdecl;
+  pcre2_match_context_free : procedure(_para1:PTpcre2_match_context_32);cdecl;
+  pcre2_set_callout : function(_para1:PTpcre2_match_context_32; _para2: tpcre2_set_callout_32_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_set_substitute_callout : function(_para1:PTpcre2_match_context_32; _para2:tpcre2_set_substitute_callout_32_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_set_depth_limit : function(_para1:PTpcre2_match_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_heap_limit : function(_para1:PTpcre2_match_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_match_limit : function(_para1:PTpcre2_match_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_offset_limit : function(_para1:PTpcre2_match_context_32; _para2:Tsize_t):Tcint;cdecl;
+  pcre2_set_recursion_limit : function(_para1:PTpcre2_match_context_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_recursion_memory_management : function(_para1:PTpcre2_match_context_32; _para2: tpcre2_malloc; _para3:tpcre2_free; _para4:pointer):Tcint;cdecl;
+  pcre2_compile : function(_para1:TPCRE2_SPTR8; _para2:Tsize_t; _para3:Tuint32_t; _para4:Pcint; _para5:Psize_t; _para6:PTpcre2_compile_context_32):Ppcre2_code_32;cdecl;
+  pcre2_code_free : procedure(_para1:PTpcre2_code_32);cdecl;
+  pcre2_code_copy : function(_para1:PTpcre2_code_32):PTpcre2_code_32;cdecl;
+  pcre2_code_copy_with_tables : function(_para1:PTpcre2_code_32):PTpcre2_code_32;cdecl;
+  pcre2_pattern_info : function(_para1:PTpcre2_code_32; _para2:Tuint32_t; _para3:pointer):Tcint;cdecl;
+  pcre2_callout_enumerate : function(_para1:PTpcre2_code_32; _para2: tpcre2_callout_enumerate_32_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_match_data_create : function(_para1:Tuint32_t; _para2:PTpcre2_general_context_32):PTpcre2_match_data_32;cdecl;
+  pcre2_match_data_create_from_pattern : function(_para1:PTpcre2_code_32; _para2:PTpcre2_general_context_32):PTpcre2_match_data_32;cdecl;
+  pcre2_dfa_match : function(_para1:PTpcre2_code_32; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_32; _para7:PTpcre2_match_context_32; _para8:Pcint; _para9:Tsize_t):Tcint;cdecl;
+  pcre2_match : function(_para1:PTpcre2_code_32; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_32; _para7:PTpcre2_match_context_32):Tcint;cdecl;
+  pcre2_match_data_free : procedure(_para1:PTpcre2_match_data_32);cdecl;
+  pcre2_get_mark : function(_para1:PTpcre2_match_data_32):TPCRE2_SPTR8;cdecl;
+  pcre2_get_match_data_size : function(_para1:PTpcre2_match_data_32):Tsize_t;cdecl;
+  pcre2_get_ovector_count : function(_para1:PTpcre2_match_data_32):Tuint32_t;cdecl;
+  pcre2_get_ovector_pointer : function(_para1:PTpcre2_match_data_32):Psize_t;cdecl;
+  pcre2_get_startchar : function(_para1:PTpcre2_match_data_32):Tsize_t;cdecl;
+  pcre2_substring_copy_byname : function(_para1:PTpcre2_match_data_32; _para2:TPCRE2_SPTR8; _para3:PTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_copy_bynumber : function(_para1:PTpcre2_match_data_32; _para2:Tuint32_t; _para3:PTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_free : procedure(_para1:PTPCRE2_UCHAR8);cdecl;
+  pcre2_substring_get_byname : function(_para1:PTpcre2_match_data_32; _para2:TPCRE2_SPTR8; _para3:PPTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_get_bynumber : function(_para1:PTpcre2_match_data_32; _para2:Tuint32_t; _para3:PPTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_length_byname : function(_para1:PTpcre2_match_data_32; _para2:TPCRE2_SPTR8; _para3:PTsize_t):Tcint;cdecl;
+  pcre2_substring_length_bynumber : function(_para1:PTpcre2_match_data_32; _para2:Tuint32_t; _para3:PTsize_t):Tcint;cdecl;
+  pcre2_substring_nametable_scan : function(_para1:PTpcre2_code_32; _para2:TPCRE2_SPTR8; _para3:PTPCRE2_SPTR8; _para4:PTPCRE2_SPTR8):Tcint;cdecl;
+  pcre2_substring_number_from_name : function(_para1:PTpcre2_code_32; _para2:TPCRE2_SPTR8):Tcint;cdecl;
+  pcre2_substring_list_free : procedure(_para1:PTPCRE2_SPTR8);cdecl;
+  pcre2_substring_list_get : function(_para1:PTpcre2_match_data_32; _para2:PPPTPCRE2_UCHAR8; _para3:PPTsize_t):Tcint;cdecl;
+  pcre2_serialize_encode : function(_para1:PPTpcre2_code_32; _para2:Tint32_t; _para3:PPTuint8_t; _para4:PTsize_t; _para5:PTpcre2_general_context_32):Tint32_t;cdecl;
+  pcre2_serialize_decode : function(_para1:PPTpcre2_code_32; _para2:Tint32_t; _para3:PTuint8_t; _para4:PTpcre2_general_context_32):Tint32_t;cdecl;
+  pcre2_serialize_get_number_of_codes : function(_para1:PTuint8_t):Tint32_t;cdecl;
+  pcre2_serialize_free : procedure(_para1:PTuint8_t);cdecl;
+  pcre2_substitute : function(_para1:PTpcre2_code_32; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_32; _para7:PTpcre2_match_context_32; _para8:TPCRE2_SPTR8; _para9:Tsize_t; _para10:PTPCRE2_UCHAR8;  _para11:PTsize_t):Tcint;cdecl;
+  pcre2_jit_compile : function(_para1:PTpcre2_code_32; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_jit_match : function(_para1:PTpcre2_code_32; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_32; _para7:PTpcre2_match_context_32):Tcint;cdecl;
+  pcre2_jit_free_unused_memory : procedure(_para1:PTpcre2_general_context_32);cdecl;
+  pcre2_jit_stack_create : function(_para1:Tsize_t; _para2:Tsize_t; _para3:PTpcre2_general_context_32):PTpcre2_jit_stack_32;cdecl;
+  pcre2_jit_stack_assign : procedure(_para1:PTpcre2_match_context_32; _para2:Tpcre2_jit_callback_32; _para3:pointer);cdecl;
+  pcre2_jit_stack_free : procedure(_para1:PTpcre2_jit_stack_32);cdecl;
+  pcre2_get_error_message : function(_para1:Tcint; _para2:PTPCRE2_UCHAR8; _para3:Tsize_t):Tcint;cdecl;
+  pcre2_maketables : function(_para1:PTpcre2_general_context_32):PTuint8_t;cdecl;
+  pcre2_maketables_free : procedure(_para1:PTpcre2_general_context_32; _para2:PTuint8_t);cdecl;
+
+function libpcre28loaded : Boolean;
+procedure Loadlibpcre28;
+procedure Freelibpcre28;
+procedure Loadlibpcre28(const lib : string);
+
+implementation
+
+uses
+{$IFDEF FPC_DOTTEDUNITS}
+  System.SysUtils, System.DynLibs;
+{$ELSE}
+  SysUtils, dynlibs;
+{$ENDIF}
+
+var
+  hlib : tlibhandle;
+
+
+function libpcre28loaded : Boolean;
+begin
+  Result:=(hLib<>NilHandle);
+end;
+
+procedure Freelibpcre28;
+
+begin
+  if hlib=nilhandle then exit;
+  FreeLibrary(hlib);
+  hlib:=NilHandle;
+  pcre2_config:=nil;
+  pcre2_general_context_copy:=nil;
+  pcre2_general_context_create:=nil;
+  pcre2_general_context_free:=nil;
+  pcre2_compile_context_copy:=nil;
+  pcre2_compile_context_create:=nil;
+  pcre2_compile_context_free:=nil;
+  pcre2_set_bsr:=nil;
+  pcre2_set_character_tables:=nil;
+  pcre2_set_compile_extra_options:=nil;
+  pcre2_set_max_pattern_length:=nil;
+  pcre2_set_newline:=nil;
+  pcre2_set_parens_nest_limit:=nil;
+  pcre2_set_compile_recursion_guard:=nil;
+  pcre2_convert_context_copy:=nil;
+  pcre2_convert_context_create:=nil;
+  pcre2_convert_context_free:=nil;
+  pcre2_set_glob_escape:=nil;
+  pcre2_set_glob_separator:=nil;
+  pcre2_pattern_convert:=nil;
+  pcre2_converted_pattern_free:=nil;
+  pcre2_match_context_copy:=nil;
+  pcre2_match_context_create:=nil;
+  pcre2_match_context_free:=nil;
+  pcre2_set_callout:=nil;
+  pcre2_set_substitute_callout:=nil;
+  pcre2_set_depth_limit:=nil;
+  pcre2_set_heap_limit:=nil;
+  pcre2_set_match_limit:=nil;
+  pcre2_set_offset_limit:=nil;
+  pcre2_set_recursion_limit:=nil;
+  pcre2_set_recursion_memory_management:=nil;
+  pcre2_compile:=nil;
+  pcre2_code_free:=nil;
+  pcre2_code_copy:=nil;
+  pcre2_code_copy_with_tables:=nil;
+  pcre2_pattern_info:=nil;
+  pcre2_callout_enumerate:=nil;
+  pcre2_match_data_create:=nil;
+  pcre2_match_data_create_from_pattern:=nil;
+  pcre2_dfa_match:=nil;
+  pcre2_match:=nil;
+  pcre2_match_data_free:=nil;
+  pcre2_get_mark:=nil;
+  pcre2_get_match_data_size:=nil;
+  pcre2_get_ovector_count:=nil;
+  pcre2_get_ovector_pointer:=nil;
+  pcre2_get_startchar:=nil;
+  pcre2_substring_copy_byname:=nil;
+  pcre2_substring_copy_bynumber:=nil;
+  pcre2_substring_free:=nil;
+  pcre2_substring_get_byname:=nil;
+  pcre2_substring_get_bynumber:=nil;
+  pcre2_substring_length_byname:=nil;
+  pcre2_substring_length_bynumber:=nil;
+  pcre2_substring_nametable_scan:=nil;
+  pcre2_substring_number_from_name:=nil;
+  pcre2_substring_list_free:=nil;
+  pcre2_substring_list_get:=nil;
+  pcre2_serialize_encode:=nil;
+  pcre2_serialize_decode:=nil;
+  pcre2_serialize_get_number_of_codes:=nil;
+  pcre2_serialize_free:=nil;
+  pcre2_substitute:=nil;
+  pcre2_jit_compile:=nil;
+  pcre2_jit_match:=nil;
+  pcre2_jit_free_unused_memory:=nil;
+  pcre2_jit_stack_create:=nil;
+  pcre2_jit_stack_assign:=nil;
+  pcre2_jit_stack_free:=nil;
+  pcre2_get_error_message:=nil;
+  pcre2_maketables:=nil;
+  pcre2_maketables_free:=nil;
+end;
+
+
+
+procedure Loadlibpcre28;
+begin
+  Loadlibpcre28(pcrelibname);
+end;
+
+
+procedure Loadlibpcre28(const lib : string);
+
+  Function GetAddr(const aName : string) : Pointer;
+
+  begin
+    Result:=GetProcAddress(hlib,aname);
+    if Result=Nil then
+      if IsConsole then
+        Writeln(stdErr,'Could not load procedure: ',aName)
+  end;
+
+begin
+  Freelibpcre28;
+  hlib:=LoadLibrary(lib);
+  if (hlib=NilHandle) then
+    raise Exception.Create(format('Could not load library: %s',[lib]));
+
+  pointer(pcre2_config):=GetAddr('pcre2_config_32');
+  pointer(pcre2_general_context_copy):=GetAddr('pcre2_general_context_copy_32');
+  pointer(pcre2_general_context_create):=GetAddr('pcre2_general_context_create_32');
+  pointer(pcre2_general_context_free):=GetAddr('pcre2_general_context_free_32');
+  pointer(pcre2_compile_context_copy):=GetAddr('pcre2_compile_context_copy_32');
+  pointer(pcre2_compile_context_create):=GetAddr('pcre2_compile_context_create_32');
+  pointer(pcre2_compile_context_free):=GetAddr('pcre2_compile_context_free_32');
+  pointer(pcre2_set_bsr):=GetAddr('pcre2_set_bsr_32');
+  pointer(pcre2_set_character_tables):=GetAddr('pcre2_set_character_tables_32');
+  pointer(pcre2_set_compile_extra_options):=GetAddr('pcre2_set_compile_extra_options_32');
+  pointer(pcre2_set_max_pattern_length):=GetAddr('pcre2_set_max_pattern_length_32');
+  pointer(pcre2_set_newline):=GetAddr('pcre2_set_newline_32');
+  pointer(pcre2_set_parens_nest_limit):=GetAddr('pcre2_set_parens_nest_limit_32');
+  pointer(pcre2_set_compile_recursion_guard):=GetAddr('pcre2_set_compile_recursion_guard_32');
+  pointer(pcre2_convert_context_copy):=GetAddr('pcre2_convert_context_copy_32');
+  pointer(pcre2_convert_context_create):=GetAddr('pcre2_convert_context_create_32');
+  pointer(pcre2_convert_context_free):=GetAddr('pcre2_convert_context_free_32');
+  pointer(pcre2_set_glob_escape):=GetAddr('pcre2_set_glob_escape_32');
+  pointer(pcre2_set_glob_separator):=GetAddr('pcre2_set_glob_separator_32');
+  pointer(pcre2_pattern_convert):=GetAddr('pcre2_pattern_convert_32');
+  pointer(pcre2_converted_pattern_free):=GetAddr('pcre2_converted_pattern_free_32');
+  pointer(pcre2_match_context_copy):=GetAddr('pcre2_match_context_copy_32');
+  pointer(pcre2_match_context_create):=GetAddr('pcre2_match_context_create_32');
+  pointer(pcre2_match_context_free):=GetAddr('pcre2_match_context_free_32');
+  pointer(pcre2_set_callout):=GetAddr('pcre2_set_callout_32');
+  pointer(pcre2_set_substitute_callout):=GetAddr('pcre2_set_substitute_callout_32');
+  pointer(pcre2_set_depth_limit):=GetAddr('pcre2_set_depth_limit_32');
+  pointer(pcre2_set_heap_limit):=GetAddr('pcre2_set_heap_limit_32');
+  pointer(pcre2_set_match_limit):=GetAddr('pcre2_set_match_limit_32');
+  pointer(pcre2_set_offset_limit):=GetAddr('pcre2_set_offset_limit_32');
+  pointer(pcre2_set_recursion_limit):=GetAddr('pcre2_set_recursion_limit_32');
+  pointer(pcre2_set_recursion_memory_management):=GetAddr('pcre2_set_recursion_memory_management_32');
+  pointer(pcre2_compile):=GetAddr('pcre2_compile_32');
+  pointer(pcre2_code_free):=GetAddr('pcre2_code_free_32');
+  pointer(pcre2_code_copy):=GetAddr('pcre2_code_copy_32');
+  pointer(pcre2_code_copy_with_tables):=GetAddr('pcre2_code_copy_with_tables_32');
+  pointer(pcre2_pattern_info):=GetAddr('pcre2_pattern_info_32');
+  pointer(pcre2_callout_enumerate):=GetAddr('pcre2_callout_enumerate_32');
+  pointer(pcre2_match_data_create):=GetAddr('pcre2_match_data_create_32');
+  pointer(pcre2_match_data_create_from_pattern):=GetAddr('pcre2_match_data_create_from_pattern_32');
+  pointer(pcre2_dfa_match):=GetAddr('pcre2_dfa_match_32');
+  pointer(pcre2_match):=GetAddr('pcre2_match_32');
+  pointer(pcre2_match_data_free):=GetAddr('pcre2_match_data_free_32');
+  pointer(pcre2_get_mark):=GetAddr('pcre2_get_mark_32');
+  pointer(pcre2_get_match_data_size):=GetAddr('pcre2_get_match_data_size_32');
+  pointer(pcre2_get_ovector_count):=GetAddr('pcre2_get_ovector_count_32');
+  pointer(pcre2_get_ovector_pointer):=GetAddr('pcre2_get_ovector_pointer_32');
+  pointer(pcre2_get_startchar):=GetAddr('pcre2_get_startchar_32');
+  pointer(pcre2_substring_copy_byname):=GetAddr('pcre2_substring_copy_byname_32');
+  pointer(pcre2_substring_copy_bynumber):=GetAddr('pcre2_substring_copy_bynumber_32');
+  pointer(pcre2_substring_free):=GetAddr('pcre2_substring_free_32');
+  pointer(pcre2_substring_get_byname):=GetAddr('pcre2_substring_get_byname_32');
+  pointer(pcre2_substring_get_bynumber):=GetAddr('pcre2_substring_get_bynumber_32');
+  pointer(pcre2_substring_length_byname):=GetAddr('pcre2_substring_length_byname_32');
+  pointer(pcre2_substring_length_bynumber):=GetAddr('pcre2_substring_length_bynumber_32');
+  pointer(pcre2_substring_nametable_scan):=GetAddr('pcre2_substring_nametable_scan_32');
+  pointer(pcre2_substring_number_from_name):=GetAddr('pcre2_substring_number_from_name_32');
+  pointer(pcre2_substring_list_free):=GetAddr('pcre2_substring_list_free_32');
+  pointer(pcre2_substring_list_get):=GetAddr('pcre2_substring_list_get_32');
+  pointer(pcre2_serialize_encode):=GetAddr('pcre2_serialize_encode_32');
+  pointer(pcre2_serialize_decode):=GetAddr('pcre2_serialize_decode_32');
+  pointer(pcre2_serialize_get_number_of_codes):=GetAddr('pcre2_serialize_get_number_of_codes_32');
+  pointer(pcre2_serialize_free):=GetAddr('pcre2_serialize_free_32');
+  pointer(pcre2_substitute):=GetAddr('pcre2_substitute_32');
+  pointer(pcre2_jit_compile):=GetAddr('pcre2_jit_compile_32');
+  pointer(pcre2_jit_match):=GetAddr('pcre2_jit_match_32');
+  pointer(pcre2_jit_free_unused_memory):=GetAddr('pcre2_jit_free_unused_memory_32');
+  pointer(pcre2_jit_stack_create):=GetAddr('pcre2_jit_stack_create_32');
+  pointer(pcre2_jit_stack_assign):=GetAddr('pcre2_jit_stack_assign_32');
+  pointer(pcre2_jit_stack_free):=GetAddr('pcre2_jit_stack_free_32');
+  pointer(pcre2_get_error_message):=GetAddr('pcre2_get_error_message_32');
+  pointer(pcre2_maketables):=GetAddr('pcre2_maketables_32');
+  pointer(pcre2_maketables_free):=GetAddr('pcre2_maketables_free_32');
+end;
+
+
+initialization
+ Loadlibpcre28;
+
+finalization
+  Freelibpcre28;
+end.

+ 510 - 0
packages/libpcre/src/libpcre2_8.pp

@@ -0,0 +1,510 @@
+{$mode objfpc}
+{$h+}
+{$IFNDEF FPC_DOTTEDUNITS}
+unit libpcre2_8;
+{$ENDIF}
+
+interface
+
+uses
+{$IFDEF FPC_DOTTEDUNITS}
+  System.CTypes;
+{$ELSE}
+  ctypes;
+{$ENDIF}
+
+const
+  {$IFDEF LINUX}
+    pcrelibname = 'libpcre2-8.so.0';
+  {$ELSE}
+    {$IFDEF windows}
+      pcrelibname = 'libpcre-1.dll'; // As used in Mingw64
+    {$ELSE}
+      {$IFDEF DARWIN}
+        pcrelibname = 'libpcre2-8.dylib';
+      {$ELSE}
+        {$ERROR: platform not supported by pcre}
+      {$ENDIF}
+    {$ENDIF}
+  {$ENDIF}
+
+{$i pcreconsts.inc}
+
+{
+  Automatically converted by H2Pas 1.0.0 from pre_pcre_8.h
+  The following command line parameters were used:
+    -c
+    -l
+    libpcre2-8
+    pre_pcre_8.h
+    -C
+    -o
+    libpcre28.pp
+    -P
+    -P
+    -t
+}
+
+{$IFDEF FPC}
+{$PACKRECORDS C}
+{$ENDIF}
+
+Type
+  tsize_t = csize_t;
+  PCRE2_SIZE = tsize_t;
+  PTsize_t = ^Tsize_t;
+  PPTsize_t = ^PTsize_t;
+  tuint32_t = cardinal;
+  Tint32_t = cuint32;
+  Tcint = cint;
+
+  Ppcre2_callout_block_8  = ^Tpcre2_callout_block_8;
+  Ppcre2_callout_block = Ppcre2_callout_block_8;
+
+  Ppcre2_callout_enumerate_block_8  = ^Tpcre2_callout_enumerate_block_8;
+  Ppcre2_callout_enumerate_block = Ppcre2_callout_enumerate_block_8;
+
+  Ppcre2_code_8  = ^Tpcre2_code_8;
+  Ppcre2_code = Ppcre2_code_8;
+
+  Ppcre2_compile_context_8  = ^Tpcre2_compile_context_8;
+  Ppcre2_compile_context = Ppcre2_compile_context_8;
+
+  Ppcre2_convert_context_8  = ^Tpcre2_convert_context_8;
+  Ppcre2_convert_context = Ppcre2_convert_context_8;
+
+  Ppcre2_general_context_8  = ^Tpcre2_general_context_8;
+  Ppcre2_general_context = Ppcre2_general_context_8;
+
+  Ppcre2_jit_stack_8  = ^Tpcre2_jit_stack_8;
+  Ppcre2_jit_stack = Ppcre2_jit_stack_8;
+
+  Ppcre2_match_context_8  = ^Tpcre2_match_context_8;
+  Ppcre2_match_context = Ppcre2_match_context_8;
+
+  Ppcre2_match_data_8  = ^Tpcre2_match_data_8;
+  Ppcre2_match_data = Ppcre2_match_data_8;
+
+  PPCRE2_SPTR8  = ^TPCRE2_SPTR8;
+  Ppcre2_substitute_callout_block_8  = ^Tpcre2_substitute_callout_block_8;
+  PPCRE2_UCHAR8  = ^TPCRE2_UCHAR8;
+  
+  Psize_t  = ^tsize_t;
+  Puint8_t  = ^byte;
+  PTuint8_t = Puint8_t;
+  PPTuint8_t = ^PTuint8_t;
+
+  TPCRE2_UCHAR8 = ansichar;
+  TPCRE2_SPTR8 = ^TPCRE2_UCHAR8;
+  TPCRE2_SPTR = TPCRE2_SPTR8;
+
+  PTPCRE2_UCHAR8 = ^TPCRE2_UCHAR8;
+  PTPCRE2_UCHAR = PTPCRE2_UCHAR8;
+
+  PCRE2_SPTR8 = TPCRE2_SPTR8;
+  PCRE2_SPTR = PCRE2_SPTR8;
+
+  PTPCRE2_SPTR8 = PCRE2_SPTR8;
+  PTPCRE2_SPTR = PTPCRE2_SPTR8;
+
+  PPTPCRE2_UCHAR8 = ^PTPCRE2_UCHAR8;
+  PPTPCRE2_UCHAR = PPTPCRE2_UCHAR8;
+
+  PPPTPCRE2_UCHAR8 = ^PPTPCRE2_UCHAR8;
+  PPPTPCRE2_UCHAR = PPPTPCRE2_UCHAR8;
+
+  Tpcre2_real_general_context_8 = record
+  end;
+  Tpcre2_general_context_8 =  Tpcre2_real_general_context_8;
+  Tpcre2_general_context = Tpcre2_general_context_8;
+
+  Ppcre2_real_general_context_8 = ^tpcre2_real_general_context_8;
+
+  PTpcre2_general_context_8 = Ppcre2_real_general_context_8;
+
+  Tpcre2_real_compile_context_8 = record
+  end;
+  Tpcre2_compile_context_8 = Tpcre2_real_compile_context_8;
+  Tpcre2_compile_context = Tpcre2_compile_context_8;
+
+  Ppcre2_real_compile_context_8 = ^Tpcre2_real_compile_context_8;
+  PTpcre2_compile_context_8 = Ppcre2_real_compile_context_8;
+
+  Tpcre2_real_match_context_8 = record
+  end;
+  Tpcre2_match_context_8 = Tpcre2_real_match_context_8;
+  Tpcre2_match_context = Tpcre2_match_context_8;
+
+  Ppcre2_real_match_context_8 = ^Tpcre2_real_match_context_8;
+  PTpcre2_match_context_8 = Ppcre2_real_match_context_8;
+
+  Tpcre2_real_convert_context_8 = record
+  end;
+  Tpcre2_convert_context_8 = Tpcre2_real_convert_context_8;
+  Tpcre2_convert_context = Tpcre2_convert_context_8;
+
+  Ppcre2_real_convert_context_8 = ^Tpcre2_real_convert_context_8;
+  PTpcre2_convert_context_8 = Ppcre2_real_convert_context_8;
+
+  Tpcre2_real_code_8 = record
+  end;
+  Tpcre2_code_8 = Tpcre2_real_code_8;
+  Tpcre2_code = Tpcre2_code_8;
+
+  Ppcre2_real_code_8 = ^Tpcre2_real_code_8;
+  PTpcre2_code_8  = Ppcre2_real_code_8;
+  PPTpcre2_code_8 = ^PTpcre2_code_8;
+
+
+  Tpcre2_real_match_data_8 = record
+  end;
+  Tpcre2_match_data_8 = Tpcre2_real_match_data_8;
+  Tpcre2_match_data = Tpcre2_match_data_8;
+
+  Ppcre2_real_match_data_8 = ^Tpcre2_real_match_data_8;
+  PTpcre2_match_data_8 = Ppcre2_real_match_data_8;
+
+
+
+  Tpcre2_real_jit_stack_8 = record
+  end;
+  Tpcre2_jit_stack_8 = Tpcre2_real_jit_stack_8;
+  Ppcre2_real_jit_stack_8 = ^Tpcre2_real_jit_stack_8;
+  PTpcre2_jit_stack_8 = Ppcre2_real_jit_stack_8;
+
+
+
+  Tpcre2_jit_callback_8 = function (_para1:pointer): PTpcre2_jit_stack_8;cdecl;
+
+  Tpcre2_callout_block_8 = record
+    version : Tuint32_t;
+    callout_number : Tuint32_t;
+    capture_top : Tuint32_t;
+    capture_last : Tuint32_t;
+    offset_vector : ^Tsize_t;
+    mark : TPCRE2_SPTR8;
+    subject : TPCRE2_SPTR8;
+    subject_length : Tsize_t;
+    start_match : Tsize_t;
+    current_position : Tsize_t;
+    pattern_position : Tsize_t;
+    next_item_length : Tsize_t;
+    callout_string_offset : Tsize_t;
+    callout_string_length : Tsize_t;
+    callout_string : TPCRE2_SPTR8;
+    callout_flags : Tuint32_t;
+  end;
+
+
+  Tpcre2_callout_enumerate_block_8 = record
+    version : Tuint32_t;
+    pattern_position : Tsize_t;
+    next_item_length : Tsize_t;
+    callout_number : Tuint32_t;
+    callout_string_offset : Tsize_t;
+    callout_string_length : Tsize_t;
+    callout_string : TPCRE2_SPTR8;
+  end;
+  PTpcre2_callout_enumerate_block_8 = ^Tpcre2_callout_enumerate_block_8;
+
+  Tpcre2_substitute_callout_block_8 = record
+    version : Tuint32_t;
+    input : TPCRE2_SPTR8;
+    output : TPCRE2_SPTR8;
+    output_offsets : array[0..1] of Tsize_t;
+    ovector : ^Tsize_t;
+    oveccount : Tuint32_t;
+    subscount : Tuint32_t;
+
+  end;
+  PTpcre2_substitute_callout_block_8 = ^  Tpcre2_substitute_callout_block_8;
+
+  tpcre2_malloc = function (_para1:Tsize_t; _para2:pointer) : Pointer; cdecl;
+  tpcre2_free = procedure (_para1:pointer; _para2:pointer); cdecl;
+  tpcre2_set_compile_recursion_guard_8_callback = function (_para1:Tuint32_t; _para2:pointer):Tcint; cdecl;
+  tpcre2_set_callout_8_callback = function (_para1:Ppcre2_callout_block_8; _para2:pointer):Tcint; cdecl;
+  tpcre2_callout_enumerate_8_callback = function (_para1: PTpcre2_callout_enumerate_block_8; _para2:pointer):Tcint; cdecl;
+  tpcre2_set_substitute_callout_8_callback =   function (_para1:Ppcre2_substitute_callout_block_8; _para2:pointer):Tcint; cdecl;
+     
+var
+  pcre2_config:function(_para1:Tuint32_t; _para2:pointer):Tcint;cdecl;
+  pcre2_general_context_copy:function(_para1:PTpcre2_general_context_8): PTpcre2_general_context_8;cdecl;
+  pcre2_general_context_create:function(_para1:tpcre2_malloc; _para2:tpcre2_free; _para3:pointer):PTpcre2_general_context_8;cdecl;
+  pcre2_general_context_free:procedure(_para1:PTpcre2_general_context_8);cdecl;
+  pcre2_compile_context_copy:function(_para1:PTpcre2_compile_context_8):PTpcre2_compile_context_8;cdecl;
+  pcre2_compile_context_create:function(_para1:PTpcre2_general_context_8):PTpcre2_compile_context_8;cdecl;
+  pcre2_compile_context_free:procedure(_para1:PTpcre2_compile_context_8);cdecl;
+  pcre2_set_bsr:function(_para1:PTpcre2_compile_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_character_tables:function(_para1:PTpcre2_compile_context_8; _para2: Puint8_t):Tcint;cdecl;
+  pcre2_set_compile_extra_options:function(_para1:PTpcre2_compile_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_max_pattern_length:function(_para1:PTpcre2_compile_context_8; _para2:Tsize_t):Tcint;cdecl;
+  pcre2_set_newline:function(_para1:PTpcre2_compile_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_parens_nest_limit:function(_para1:PTpcre2_compile_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_compile_recursion_guard:function(_para1:PTpcre2_compile_context_8; _para2: tpcre2_set_compile_recursion_guard_8_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_convert_context_copy:function(_para1:PTpcre2_convert_context_8):PTpcre2_convert_context_8;cdecl;
+  pcre2_convert_context_create:function(_para1:PTpcre2_general_context_8):PTpcre2_convert_context_8;cdecl;
+  pcre2_convert_context_free:procedure(_para1:PTpcre2_convert_context_8);cdecl;
+  pcre2_set_glob_escape:function(_para1:PTpcre2_convert_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_glob_separator:function(_para1:PTpcre2_convert_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_pattern_convert:function(_para1:TPCRE2_SPTR8; _para2:Tsize_t; _para3:Tuint32_t; _para4:PPTPCRE2_UCHAR8; _para5: Psize_t;  _para6:PTpcre2_convert_context_8):Tcint;cdecl;
+  pcre2_converted_pattern_free:procedure(_para1:PTPCRE2_UCHAR8);cdecl;
+  pcre2_match_context_copy:function(_para1:PTpcre2_match_context_8):PTpcre2_match_context_8;cdecl;
+  pcre2_match_context_create:function(_para1:PTpcre2_general_context_8):PTpcre2_match_context_8;cdecl;
+  pcre2_match_context_free:procedure(_para1:PTpcre2_match_context_8);cdecl;
+  pcre2_set_callout:function(_para1:PTpcre2_match_context_8; _para2: tpcre2_set_callout_8_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_set_substitute_callout:function(_para1:PTpcre2_match_context_8; _para2:tpcre2_set_substitute_callout_8_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_set_depth_limit:function(_para1:PTpcre2_match_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_heap_limit:function(_para1:PTpcre2_match_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_match_limit:function(_para1:PTpcre2_match_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_offset_limit:function(_para1:PTpcre2_match_context_8; _para2:Tsize_t):Tcint;cdecl;
+  pcre2_set_recursion_limit:function(_para1:PTpcre2_match_context_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_set_recursion_memory_management:function(_para1:PTpcre2_match_context_8; _para2: tpcre2_malloc; _para3:tpcre2_free; _para4:pointer):Tcint;cdecl;
+  pcre2_compile:function(_para1:TPCRE2_SPTR8; _para2:Tsize_t; _para3:Tuint32_t; _para4:Pcint; _para5:Psize_t; _para6:PTpcre2_compile_context_8):Ppcre2_code_8;cdecl;
+  pcre2_code_free:procedure(_para1:PTpcre2_code_8);cdecl;
+  pcre2_code_copy:function(_para1:PTpcre2_code_8):PTpcre2_code_8;cdecl;
+  pcre2_code_copy_with_tables:function(_para1:PTpcre2_code_8):PTpcre2_code_8;cdecl;
+  pcre2_pattern_info:function(_para1:PTpcre2_code_8; _para2:Tuint32_t; _para3:pointer):Tcint;cdecl;
+  pcre2_callout_enumerate:function(_para1:PTpcre2_code_8; _para2: tpcre2_callout_enumerate_8_callback; _para3:pointer):Tcint;cdecl;
+  pcre2_match_data_create:function(_para1:Tuint32_t; _para2:PTpcre2_general_context_8):PTpcre2_match_data_8;cdecl;
+  pcre2_match_data_create_from_pattern:function(_para1:PTpcre2_code_8; _para2:PTpcre2_general_context_8):PTpcre2_match_data_8;cdecl;
+  pcre2_dfa_match:function(_para1:PTpcre2_code_8; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_8; _para7:PTpcre2_match_context_8; _para8:Pcint; _para9:Tsize_t):Tcint;cdecl;
+  pcre2_match:function(_para1:PTpcre2_code_8; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_8; _para7:PTpcre2_match_context_8):Tcint;cdecl;
+  pcre2_match_data_free:procedure(_para1:PTpcre2_match_data_8);cdecl;
+  pcre2_get_mark:function(_para1:PTpcre2_match_data_8):TPCRE2_SPTR8;cdecl;
+  pcre2_get_match_data_size:function(_para1:PTpcre2_match_data_8):Tsize_t;cdecl;
+  pcre2_get_ovector_count:function(_para1:PTpcre2_match_data_8):Tuint32_t;cdecl;
+  pcre2_get_ovector_pointer:function(_para1:PTpcre2_match_data_8):Psize_t;cdecl;
+  pcre2_get_startchar:function(_para1:PTpcre2_match_data_8):Tsize_t;cdecl;
+  pcre2_substring_copy_byname:function(_para1:PTpcre2_match_data_8; _para2:TPCRE2_SPTR8; _para3:PTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_copy_bynumber:function(_para1:PTpcre2_match_data_8; _para2:Tuint32_t; _para3:PTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_free:procedure(_para1:PTPCRE2_UCHAR8);cdecl;
+  pcre2_substring_get_byname:function(_para1:PTpcre2_match_data_8; _para2:TPCRE2_SPTR8; _para3:PPTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_get_bynumber:function(_para1:PTpcre2_match_data_8; _para2:Tuint32_t; _para3:PPTPCRE2_UCHAR8; _para4:PTsize_t):Tcint;cdecl;
+  pcre2_substring_length_byname:function(_para1:PTpcre2_match_data_8; _para2:TPCRE2_SPTR8; _para3:PTsize_t):Tcint;cdecl;
+  pcre2_substring_length_bynumber:function(_para1:PTpcre2_match_data_8; _para2:Tuint32_t; _para3:PTsize_t):Tcint;cdecl;
+  pcre2_substring_nametable_scan:function(_para1:PTpcre2_code_8; _para2:TPCRE2_SPTR8; _para3:PTPCRE2_SPTR8; _para4:PTPCRE2_SPTR8):Tcint;cdecl;
+  pcre2_substring_number_from_name:function(_para1:PTpcre2_code_8; _para2:TPCRE2_SPTR8):Tcint;cdecl;
+  pcre2_substring_list_free:procedure(_para1:PTPCRE2_SPTR8);cdecl;
+  pcre2_substring_list_get:function(_para1:PTpcre2_match_data_8; _para2:PPPTPCRE2_UCHAR8; _para3:PPTsize_t):Tcint;cdecl;
+  pcre2_serialize_encode:function(_para1:PPTpcre2_code_8; _para2:Tint32_t; _para3:PPTuint8_t; _para4:PTsize_t; _para5:PTpcre2_general_context_8):Tint32_t;cdecl;
+  pcre2_serialize_decode:function(_para1:PPTpcre2_code_8; _para2:Tint32_t; _para3:PTuint8_t; _para4:PTpcre2_general_context_8):Tint32_t;cdecl;
+  pcre2_serialize_get_number_of_codes:function(_para1:PTuint8_t):Tint32_t;cdecl;
+  pcre2_serialize_free:procedure(_para1:PTuint8_t);cdecl;
+  pcre2_substitute:function(_para1:PTpcre2_code_8; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_8; _para7:PTpcre2_match_context_8; _para8:TPCRE2_SPTR8; _para9:Tsize_t; _para10:PTPCRE2_UCHAR8;  _para11:PTsize_t):Tcint;cdecl;
+  pcre2_jit_compile:function(_para1:PTpcre2_code_8; _para2:Tuint32_t):Tcint;cdecl;
+  pcre2_jit_match:function(_para1:PTpcre2_code_8; _para2:TPCRE2_SPTR8; _para3:Tsize_t; _para4:Tsize_t; _para5:Tuint32_t; _para6:PTpcre2_match_data_8; _para7:PTpcre2_match_context_8):Tcint;cdecl;
+  pcre2_jit_free_unused_memory:procedure(_para1:PTpcre2_general_context_8);cdecl;
+  pcre2_jit_stack_create:function(_para1:Tsize_t; _para2:Tsize_t; _para3:PTpcre2_general_context_8):PTpcre2_jit_stack_8;cdecl;
+  pcre2_jit_stack_assign:procedure(_para1:PTpcre2_match_context_8; _para2:Tpcre2_jit_callback_8; _para3:pointer);cdecl;
+  pcre2_jit_stack_free:procedure(_para1:PTpcre2_jit_stack_8);cdecl;
+  pcre2_get_error_message:function(_para1:Tcint; _para2:PTPCRE2_UCHAR8; _para3:Tsize_t):Tcint;cdecl;
+  pcre2_maketables:function(_para1:PTpcre2_general_context_8):PTuint8_t;cdecl;
+  pcre2_maketables_free:procedure(_para1:PTpcre2_general_context_8; _para2:PTuint8_t);cdecl;
+
+function libpcre28loaded : Boolean;
+procedure Loadlibpcre28; overload;
+procedure Loadlibpcre28(const lib : string); overload;
+procedure Freelibpcre28;
+
+implementation
+
+uses
+{$IFDEF FPC_DOTTEDUNITS}
+  System.SysUtils, System.DynLibs;
+{$ELSE}
+  SysUtils, dynlibs;
+{$ENDIF}
+
+
+var
+  hlib : tlibhandle;
+
+function libpcre28loaded : Boolean;
+begin
+  Result:=(hLib<>NilHandle);
+end;
+
+procedure Freelibpcre28;
+
+begin
+  if hlib=nilhandle then exit;
+  FreeLibrary(hlib);
+  hlib:=NilHandle;
+  pcre2_config:=nil;
+  pcre2_general_context_copy:=nil;
+  pcre2_general_context_create:=nil;
+  pcre2_general_context_free:=nil;
+  pcre2_compile_context_copy:=nil;
+  pcre2_compile_context_create:=nil;
+  pcre2_compile_context_free:=nil;
+  pcre2_set_bsr:=nil;
+  pcre2_set_character_tables:=nil;
+  pcre2_set_compile_extra_options:=nil;
+  pcre2_set_max_pattern_length:=nil;
+  pcre2_set_newline:=nil;
+  pcre2_set_parens_nest_limit:=nil;
+  pcre2_set_compile_recursion_guard:=nil;
+  pcre2_convert_context_copy:=nil;
+  pcre2_convert_context_create:=nil;
+  pcre2_convert_context_free:=nil;
+  pcre2_set_glob_escape:=nil;
+  pcre2_set_glob_separator:=nil;
+  pcre2_pattern_convert:=nil;
+  pcre2_converted_pattern_free:=nil;
+  pcre2_match_context_copy:=nil;
+  pcre2_match_context_create:=nil;
+  pcre2_match_context_free:=nil;
+  pcre2_set_callout:=nil;
+  pcre2_set_substitute_callout:=nil;
+  pcre2_set_depth_limit:=nil;
+  pcre2_set_heap_limit:=nil;
+  pcre2_set_match_limit:=nil;
+  pcre2_set_offset_limit:=nil;
+  pcre2_set_recursion_limit:=nil;
+  pcre2_set_recursion_memory_management:=nil;
+  pcre2_compile:=nil;
+  pcre2_code_free:=nil;
+  pcre2_code_copy:=nil;
+  pcre2_code_copy_with_tables:=nil;
+  pcre2_pattern_info:=nil;
+  pcre2_callout_enumerate:=nil;
+  pcre2_match_data_create:=nil;
+  pcre2_match_data_create_from_pattern:=nil;
+  pcre2_dfa_match:=nil;
+  pcre2_match:=nil;
+  pcre2_match_data_free:=nil;
+  pcre2_get_mark:=nil;
+  pcre2_get_match_data_size:=nil;
+  pcre2_get_ovector_count:=nil;
+  pcre2_get_ovector_pointer:=nil;
+  pcre2_get_startchar:=nil;
+  pcre2_substring_copy_byname:=nil;
+  pcre2_substring_copy_bynumber:=nil;
+  pcre2_substring_free:=nil;
+  pcre2_substring_get_byname:=nil;
+  pcre2_substring_get_bynumber:=nil;
+  pcre2_substring_length_byname:=nil;
+  pcre2_substring_length_bynumber:=nil;
+  pcre2_substring_nametable_scan:=nil;
+  pcre2_substring_number_from_name:=nil;
+  pcre2_substring_list_free:=nil;
+  pcre2_substring_list_get:=nil;
+  pcre2_serialize_encode:=nil;
+  pcre2_serialize_decode:=nil;
+  pcre2_serialize_get_number_of_codes:=nil;
+  pcre2_serialize_free:=nil;
+  pcre2_substitute:=nil;
+  pcre2_jit_compile:=nil;
+  pcre2_jit_match:=nil;
+  pcre2_jit_free_unused_memory:=nil;
+  pcre2_jit_stack_create:=nil;
+  pcre2_jit_stack_assign:=nil;
+  pcre2_jit_stack_free:=nil;
+  pcre2_get_error_message:=nil;
+  pcre2_maketables:=nil;
+  pcre2_maketables_free:=nil;
+end;
+
+procedure Loadlibpcre28;
+begin
+  Loadlibpcre28(pcrelibname);
+end;
+
+procedure Loadlibpcre28(const lib : string);
+
+  Function GetAddr(const aName : string) : Pointer;
+
+  begin
+    Result:=GetProcAddress(hlib,aname);
+    if Result=Nil then
+      if IsConsole then
+        Writeln(stdErr,'Could not load procedure: ',aName)
+  end;
+
+begin
+  Freelibpcre28;
+  hlib:=LoadLibrary(lib);
+  if (hlib=NilHandle) then
+    raise Exception.Create(format('Could not load library: %s',[lib]));
+  pointer(pcre2_config):=GetAddr('pcre2_config_8');
+  pointer(pcre2_general_context_copy):=GetAddr('pcre2_general_context_copy_8');
+  pointer(pcre2_general_context_create):=GetAddr('pcre2_general_context_create_8');
+  pointer(pcre2_general_context_free):=GetAddr('pcre2_general_context_free_8');
+  pointer(pcre2_compile_context_copy):=GetAddr('pcre2_compile_context_copy_8');
+  pointer(pcre2_compile_context_create):=GetAddr('pcre2_compile_context_create_8');
+  pointer(pcre2_compile_context_free):=GetAddr('pcre2_compile_context_free_8');
+  pointer(pcre2_set_bsr):=GetAddr('pcre2_set_bsr_8');
+  pointer(pcre2_set_character_tables):=GetAddr('pcre2_set_character_tables_8');
+  pointer(pcre2_set_compile_extra_options):=GetAddr('pcre2_set_compile_extra_options_8');
+  pointer(pcre2_set_max_pattern_length):=GetAddr('pcre2_set_max_pattern_length_8');
+  pointer(pcre2_set_newline):=GetAddr('pcre2_set_newline_8');
+  pointer(pcre2_set_parens_nest_limit):=GetAddr('pcre2_set_parens_nest_limit_8');
+  pointer(pcre2_set_compile_recursion_guard):=GetAddr('pcre2_set_compile_recursion_guard_8');
+  pointer(pcre2_convert_context_copy):=GetAddr('pcre2_convert_context_copy_8');
+  pointer(pcre2_convert_context_create):=GetAddr('pcre2_convert_context_create_8');
+  pointer(pcre2_convert_context_free):=GetAddr('pcre2_convert_context_free_8');
+  pointer(pcre2_set_glob_escape):=GetAddr('pcre2_set_glob_escape_8');
+  pointer(pcre2_set_glob_separator):=GetAddr('pcre2_set_glob_separator_8');
+  pointer(pcre2_pattern_convert):=GetAddr('pcre2_pattern_convert_8');
+  pointer(pcre2_converted_pattern_free):=GetAddr('pcre2_converted_pattern_free_8');
+  pointer(pcre2_match_context_copy):=GetAddr('pcre2_match_context_copy_8');
+  pointer(pcre2_match_context_create):=GetAddr('pcre2_match_context_create_8');
+  pointer(pcre2_match_context_free):=GetAddr('pcre2_match_context_free_8');
+  pointer(pcre2_set_callout):=GetAddr('pcre2_set_callout_8');
+  pointer(pcre2_set_substitute_callout):=GetAddr('pcre2_set_substitute_callout_8');
+  pointer(pcre2_set_depth_limit):=GetAddr('pcre2_set_depth_limit_8');
+  pointer(pcre2_set_heap_limit):=GetAddr('pcre2_set_heap_limit_8');
+  pointer(pcre2_set_match_limit):=GetAddr('pcre2_set_match_limit_8');
+  pointer(pcre2_set_offset_limit):=GetAddr('pcre2_set_offset_limit_8');
+  pointer(pcre2_set_recursion_limit):=GetAddr('pcre2_set_recursion_limit_8');
+  pointer(pcre2_set_recursion_memory_management):=GetAddr('pcre2_set_recursion_memory_management_8');
+  pointer(pcre2_compile):=GetAddr('pcre2_compile_8');
+  pointer(pcre2_code_free):=GetAddr('pcre2_code_free_8');
+  pointer(pcre2_code_copy):=GetAddr('pcre2_code_copy_8');
+  pointer(pcre2_code_copy_with_tables):=GetAddr('pcre2_code_copy_with_tables_8');
+  pointer(pcre2_pattern_info):=GetAddr('pcre2_pattern_info_8');
+  pointer(pcre2_callout_enumerate):=GetAddr('pcre2_callout_enumerate_8');
+  pointer(pcre2_match_data_create):=GetAddr('pcre2_match_data_create_8');
+  pointer(pcre2_match_data_create_from_pattern):=GetAddr('pcre2_match_data_create_from_pattern_8');
+  pointer(pcre2_dfa_match):=GetAddr('pcre2_dfa_match_8');
+  pointer(pcre2_match):=GetAddr('pcre2_match_8');
+  pointer(pcre2_match_data_free):=GetAddr('pcre2_match_data_free_8');
+  pointer(pcre2_get_mark):=GetAddr('pcre2_get_mark_8');
+  pointer(pcre2_get_match_data_size):=GetAddr('pcre2_get_match_data_size_8');
+  pointer(pcre2_get_ovector_count):=GetAddr('pcre2_get_ovector_count_8');
+  pointer(pcre2_get_ovector_pointer):=GetAddr('pcre2_get_ovector_pointer_8');
+  pointer(pcre2_get_startchar):=GetAddr('pcre2_get_startchar_8');
+  pointer(pcre2_substring_copy_byname):=GetAddr('pcre2_substring_copy_byname_8');
+  pointer(pcre2_substring_copy_bynumber):=GetAddr('pcre2_substring_copy_bynumber_8');
+  pointer(pcre2_substring_free):=GetAddr('pcre2_substring_free_8');
+  pointer(pcre2_substring_get_byname):=GetAddr('pcre2_substring_get_byname_8');
+  pointer(pcre2_substring_get_bynumber):=GetAddr('pcre2_substring_get_bynumber_8');
+  pointer(pcre2_substring_length_byname):=GetAddr('pcre2_substring_length_byname_8');
+  pointer(pcre2_substring_length_bynumber):=GetAddr('pcre2_substring_length_bynumber_8');
+  pointer(pcre2_substring_nametable_scan):=GetAddr('pcre2_substring_nametable_scan_8');
+  pointer(pcre2_substring_number_from_name):=GetAddr('pcre2_substring_number_from_name_8');
+  pointer(pcre2_substring_list_free):=GetAddr('pcre2_substring_list_free_8');
+  pointer(pcre2_substring_list_get):=GetAddr('pcre2_substring_list_get_8');
+  pointer(pcre2_serialize_encode):=GetAddr('pcre2_serialize_encode_8');
+  pointer(pcre2_serialize_decode):=GetAddr('pcre2_serialize_decode_8');
+  pointer(pcre2_serialize_get_number_of_codes):=GetAddr('pcre2_serialize_get_number_of_codes_8');
+  pointer(pcre2_serialize_free):=GetAddr('pcre2_serialize_free_8');
+  pointer(pcre2_substitute):=GetAddr('pcre2_substitute_8');
+  pointer(pcre2_jit_compile):=GetAddr('pcre2_jit_compile_8');
+  pointer(pcre2_jit_match):=GetAddr('pcre2_jit_match_8');
+  pointer(pcre2_jit_free_unused_memory):=GetAddr('pcre2_jit_free_unused_memory_8');
+  pointer(pcre2_jit_stack_create):=GetAddr('pcre2_jit_stack_create_8');
+  pointer(pcre2_jit_stack_assign):=GetAddr('pcre2_jit_stack_assign_8');
+  pointer(pcre2_jit_stack_free):=GetAddr('pcre2_jit_stack_free_8');
+  pointer(pcre2_get_error_message):=GetAddr('pcre2_get_error_message_8');
+  pointer(pcre2_maketables):=GetAddr('pcre2_maketables_8');
+  pointer(pcre2_maketables_free):=GetAddr('pcre2_maketables_free_8');
+end;
+
+
+initialization
+  Loadlibpcre28;
+
+finalization
+  Freelibpcre28;
+end.

+ 308 - 0
packages/libpcre/src/pcreconsts.inc

@@ -0,0 +1,308 @@
+
+const
+  PCRE2_MAJOR = 10;    
+  PCRE2_MINOR = 39;    
+  PCRE2_DATE = '2021-10-29';    
+
+  PCRE2_ANCHORED = $80000000;    
+  PCRE2_NO_UTF_CHECK = $40000000;    
+  PCRE2_ENDANCHORED = $20000000;    
+
+
+  PCRE2_ALLOW_EMPTY_CLASS = $00000001;
+  PCRE2_ALT_BSUX = $00000002;
+  PCRE2_AUTO_CALLOUT = $00000004;
+  PCRE2_CASELESS = $00000008;
+  PCRE2_DOLLAR_ENDONLY = $00000010;
+  PCRE2_DOTALL = $00000020;
+  PCRE2_DUPNAMES = $00000040;
+  PCRE2_EXTENDED = $00000080;
+  PCRE2_FIRSTLINE = $00000100;
+  PCRE2_MATCH_UNSET_BACKREF = $00000200;
+
+  PCRE2_MULTILINE = $00000400;
+  PCRE2_NEVER_UCP = $00000800;
+  PCRE2_NEVER_UTF = $00001000;
+  PCRE2_NO_AUTO_CAPTURE = $00002000;
+  PCRE2_NO_AUTO_POSSESS = $00004000;
+  PCRE2_NO_DOTSTAR_ANCHOR = $00008000;
+  PCRE2_NO_START_OPTIMIZE = $00010000;
+  PCRE2_UCP = $00020000;
+  PCRE2_UNGREEDY = $00040000;
+  PCRE2_UTF = $00080000;
+  PCRE2_NEVER_BACKSLASH_C = $00100000;
+  PCRE2_ALT_CIRCUMFLEX = $00200000;
+  PCRE2_ALT_VERBNAMES = $00400000;
+  PCRE2_USE_OFFSET_LIMIT = $00800000;
+  PCRE2_EXTENDED_MORE = $01000000;
+  PCRE2_LITERAL = $02000000;
+  PCRE2_MATCH_INVALID_UTF = $04000000;
+
+  PCRE2_EXTRA_ALLOW_SURROGATE_ESCAPES = $00000001;
+  PCRE2_EXTRA_BAD_ESCAPE_IS_LITERAL = $00000002;
+  PCRE2_EXTRA_MATCH_WORD = $00000004;
+  PCRE2_EXTRA_MATCH_LINE = $00000008;
+  PCRE2_EXTRA_ESCAPED_CR_IS_LF = $00000010;
+  PCRE2_EXTRA_ALT_BSUX = $00000020;
+  PCRE2_EXTRA_ALLOW_LOOKAROUND_BSK = $00000040;
+
+
+  PCRE2_JIT_COMPLETE = $00000001;
+  PCRE2_JIT_PARTIAL_SOFT = $00000002;
+  PCRE2_JIT_PARTIAL_HARD = $00000004;
+  PCRE2_JIT_INVALID_UTF = $00000100;
+
+  PCRE2_NOTBOL = $00000001;
+  PCRE2_NOTEOL = $00000002;
+  PCRE2_NOTEMPTY = $00000004;
+
+  PCRE2_NOTEMPTY_ATSTART = $00000008;
+  PCRE2_PARTIAL_SOFT = $00000010;
+  PCRE2_PARTIAL_HARD = $00000020;
+  PCRE2_DFA_RESTART = $00000040;
+  PCRE2_DFA_SHORTEST = $00000080;
+  PCRE2_SUBSTITUTE_GLOBAL = $00000100;
+  PCRE2_SUBSTITUTE_EXTENDED = $00000200;
+  PCRE2_SUBSTITUTE_UNSET_EMPTY = $00000400;
+  PCRE2_SUBSTITUTE_UNKNOWN_UNSET = $00000800;
+  PCRE2_SUBSTITUTE_OVERFLOW_LENGTH = $00001000;
+  PCRE2_NO_JIT = $00002000;
+  PCRE2_COPY_MATCHED_SUBJECT = $00004000;
+  PCRE2_SUBSTITUTE_LITERAL = $00008000;
+  PCRE2_SUBSTITUTE_MATCHED = $00010000;
+  PCRE2_SUBSTITUTE_REPLACEMENT_ONLY = $00020000;
+
+  PCRE2_CONVERT_UTF = $00000001;
+  PCRE2_CONVERT_NO_UTF_CHECK = $00000002;
+  PCRE2_CONVERT_POSIX_BASIC = $00000004;
+  PCRE2_CONVERT_POSIX_EXTENDED = $00000008;
+  PCRE2_CONVERT_GLOB = $00000010;
+  PCRE2_CONVERT_GLOB_NO_WILD_SEPARATOR = $00000030;
+  PCRE2_CONVERT_GLOB_NO_STARSTAR = $00000050;
+
+  PCRE2_NEWLINE_CR = 1;
+  PCRE2_NEWLINE_LF = 2;
+  PCRE2_NEWLINE_CRLF = 3;
+  PCRE2_NEWLINE_ANY = 4;
+  PCRE2_NEWLINE_ANYCRLF = 5;
+  PCRE2_NEWLINE_NUL = 6;
+  PCRE2_BSR_UNICODE = 1;
+  PCRE2_BSR_ANYCRLF = 2;
+
+  PCRE2_ERROR_END_BACKSLASH = 101;
+  PCRE2_ERROR_END_BACKSLASH_C = 102;
+  PCRE2_ERROR_UNKNOWN_ESCAPE = 103;
+  PCRE2_ERROR_QUANTIFIER_OUT_OF_ORDER = 104;
+  PCRE2_ERROR_QUANTIFIER_TOO_BIG = 105;
+  PCRE2_ERROR_MISSING_SQUARE_BRACKET = 106;
+  PCRE2_ERROR_ESCAPE_INVALID_IN_CLASS = 107;
+  PCRE2_ERROR_CLASS_RANGE_ORDER = 108;
+  PCRE2_ERROR_QUANTIFIER_INVALID = 109;
+  PCRE2_ERROR_INTERNAL_UNEXPECTED_REPEAT = 110;
+  PCRE2_ERROR_INVALID_AFTER_PARENS_QUERY = 111;
+  PCRE2_ERROR_POSIX_CLASS_NOT_IN_CLASS = 112;
+  PCRE2_ERROR_POSIX_NO_SUPPORT_COLLATING = 113;
+  PCRE2_ERROR_MISSING_CLOSING_PARENTHESIS = 114;
+  PCRE2_ERROR_BAD_SUBPATTERN_REFERENCE = 115;
+  PCRE2_ERROR_NULL_PATTERN = 116;
+  PCRE2_ERROR_BAD_OPTIONS = 117;
+  PCRE2_ERROR_MISSING_COMMENT_CLOSING = 118;
+  PCRE2_ERROR_PARENTHESES_NEST_TOO_DEEP = 119;
+  PCRE2_ERROR_PATTERN_TOO_LARGE = 120;
+  PCRE2_ERROR_HEAP_FAILED = 121;
+  PCRE2_ERROR_UNMATCHED_CLOSING_PARENTHESIS = 122;
+  PCRE2_ERROR_INTERNAL_CODE_OVERFLOW = 123;
+  PCRE2_ERROR_MISSING_CONDITION_CLOSING = 124;
+  PCRE2_ERROR_LOOKBEHIND_NOT_FIXED_LENGTH = 125;
+  PCRE2_ERROR_ZERO_RELATIVE_REFERENCE = 126;
+  PCRE2_ERROR_TOO_MANY_CONDITION_BRANCHES = 127;
+  PCRE2_ERROR_CONDITION_ASSERTION_EXPECTED = 128;
+  PCRE2_ERROR_BAD_RELATIVE_REFERENCE = 129;
+  PCRE2_ERROR_UNKNOWN_POSIX_CLASS = 130;
+  PCRE2_ERROR_INTERNAL_STUDY_ERROR = 131;
+  PCRE2_ERROR_UNICODE_NOT_SUPPORTED = 132;
+  PCRE2_ERROR_PARENTHESES_STACK_CHECK = 133;
+  PCRE2_ERROR_CODE_POINT_TOO_BIG = 134;
+  PCRE2_ERROR_LOOKBEHIND_TOO_COMPLICATED = 135;
+  PCRE2_ERROR_LOOKBEHIND_INVALID_BACKSLASH_C = 136;
+  PCRE2_ERROR_UNSUPPORTED_ESCAPE_SEQUENCE = 137;
+  PCRE2_ERROR_CALLOUT_NUMBER_TOO_BIG = 138;
+  PCRE2_ERROR_MISSING_CALLOUT_CLOSING = 139;
+  PCRE2_ERROR_ESCAPE_INVALID_IN_VERB = 140;
+  PCRE2_ERROR_UNRECOGNIZED_AFTER_QUERY_P = 141;
+  PCRE2_ERROR_MISSING_NAME_TERMINATOR = 142;
+  PCRE2_ERROR_DUPLICATE_SUBPATTERN_NAME = 143;
+  PCRE2_ERROR_INVALID_SUBPATTERN_NAME = 144;
+  PCRE2_ERROR_UNICODE_PROPERTIES_UNAVAILABLE = 145;
+  PCRE2_ERROR_MALFORMED_UNICODE_PROPERTY = 146;
+  PCRE2_ERROR_UNKNOWN_UNICODE_PROPERTY = 147;
+  PCRE2_ERROR_SUBPATTERN_NAME_TOO_LONG = 148;
+  PCRE2_ERROR_TOO_MANY_NAMED_SUBPATTERNS = 149;
+  PCRE2_ERROR_CLASS_INVALID_RANGE = 150;
+  PCRE2_ERROR_OCTAL_BYTE_TOO_BIG = 151;
+  PCRE2_ERROR_INTERNAL_OVERRAN_WORKSPACE = 152;
+  PCRE2_ERROR_INTERNAL_MISSING_SUBPATTERN = 153;
+  PCRE2_ERROR_DEFINE_TOO_MANY_BRANCHES = 154;
+  PCRE2_ERROR_BACKSLASH_O_MISSING_BRACE = 155;
+  PCRE2_ERROR_INTERNAL_UNKNOWN_NEWLINE = 156;
+  PCRE2_ERROR_BACKSLASH_G_SYNTAX = 157;
+  PCRE2_ERROR_PARENS_QUERY_R_MISSING_CLOSING = 158;
+
+  PCRE2_ERROR_VERB_ARGUMENT_NOT_ALLOWED = 159;
+  PCRE2_ERROR_VERB_UNKNOWN = 160;
+  PCRE2_ERROR_SUBPATTERN_NUMBER_TOO_BIG = 161;
+  PCRE2_ERROR_SUBPATTERN_NAME_EXPECTED = 162;
+  PCRE2_ERROR_INTERNAL_PARSED_OVERFLOW = 163;
+  PCRE2_ERROR_INVALID_OCTAL = 164;
+  PCRE2_ERROR_SUBPATTERN_NAMES_MISMATCH = 165;
+  PCRE2_ERROR_MARK_MISSING_ARGUMENT = 166;
+  PCRE2_ERROR_INVALID_HEXADECIMAL = 167;
+  PCRE2_ERROR_BACKSLASH_C_SYNTAX = 168;
+  PCRE2_ERROR_BACKSLASH_K_SYNTAX = 169;
+  PCRE2_ERROR_INTERNAL_BAD_CODE_LOOKBEHINDS = 170;
+  PCRE2_ERROR_BACKSLASH_N_IN_CLASS = 171;
+  PCRE2_ERROR_CALLOUT_STRING_TOO_LONG = 172;
+  PCRE2_ERROR_UNICODE_DISALLOWED_CODE_POINT = 173;
+  PCRE2_ERROR_UTF_IS_DISABLED = 174;
+  PCRE2_ERROR_UCP_IS_DISABLED = 175;
+  PCRE2_ERROR_VERB_NAME_TOO_LONG = 176;
+  PCRE2_ERROR_BACKSLASH_U_CODE_POINT_TOO_BIG = 177;
+  PCRE2_ERROR_MISSING_OCTAL_OR_HEX_DIGITS = 178;
+  PCRE2_ERROR_VERSION_CONDITION_SYNTAX = 179;
+  PCRE2_ERROR_INTERNAL_BAD_CODE_AUTO_POSSESS = 180;
+  PCRE2_ERROR_CALLOUT_NO_STRING_DELIMITER = 181;
+  PCRE2_ERROR_CALLOUT_BAD_STRING_DELIMITER = 182;
+  PCRE2_ERROR_BACKSLASH_C_CALLER_DISABLED = 183;
+  PCRE2_ERROR_QUERY_BARJX_NEST_TOO_DEEP = 184;
+  PCRE2_ERROR_BACKSLASH_C_LIBRARY_DISABLED = 185;
+  PCRE2_ERROR_PATTERN_TOO_COMPLICATED = 186;
+  PCRE2_ERROR_LOOKBEHIND_TOO_LONG = 187;
+  PCRE2_ERROR_PATTERN_STRING_TOO_LONG = 188;
+  PCRE2_ERROR_INTERNAL_BAD_CODE = 189;
+  PCRE2_ERROR_INTERNAL_BAD_CODE_IN_SKIP = 190;
+  PCRE2_ERROR_NO_SURROGATES_IN_UTF16 = 191;
+  PCRE2_ERROR_BAD_LITERAL_OPTIONS = 192;
+  PCRE2_ERROR_SUPPORTED_ONLY_IN_UNICODE = 193;
+  PCRE2_ERROR_INVALID_HYPHEN_IN_OPTIONS = 194;
+  PCRE2_ERROR_ALPHA_ASSERTION_UNKNOWN = 195;
+  PCRE2_ERROR_SCRIPT_RUN_NOT_AVAILABLE = 196;
+  PCRE2_ERROR_TOO_MANY_CAPTURES = 197;
+  PCRE2_ERROR_CONDITION_ATOMIC_ASSERTION_EXPECTED = 198;
+  PCRE2_ERROR_BACKSLASH_K_IN_LOOKAROUND = 199;
+
+  PCRE2_ERROR_NOMATCH = -(1);
+  PCRE2_ERROR_PARTIAL = -(2);
+
+  PCRE2_ERROR_UTF8_ERR1 = -(3);
+  PCRE2_ERROR_UTF8_ERR2 = -(4);
+  PCRE2_ERROR_UTF8_ERR3 = -(5);
+  PCRE2_ERROR_UTF8_ERR4 = -(6);
+  PCRE2_ERROR_UTF8_ERR5 = -(7);
+  PCRE2_ERROR_UTF8_ERR6 = -(8);
+  PCRE2_ERROR_UTF8_ERR7 = -(9);
+  PCRE2_ERROR_UTF8_ERR8 = -(10);
+  PCRE2_ERROR_UTF8_ERR9 = -(11);
+  PCRE2_ERROR_UTF8_ERR10 = -(12);
+  PCRE2_ERROR_UTF8_ERR11 = -(13);
+  PCRE2_ERROR_UTF8_ERR12 = -(14);
+  PCRE2_ERROR_UTF8_ERR13 = -(15);
+  PCRE2_ERROR_UTF8_ERR14 = -(16);
+  PCRE2_ERROR_UTF8_ERR15 = -(17);
+  PCRE2_ERROR_UTF8_ERR16 = -(18);
+  PCRE2_ERROR_UTF8_ERR17 = -(19);
+  PCRE2_ERROR_UTF8_ERR18 = -(20);
+  PCRE2_ERROR_UTF8_ERR19 = -(21);
+  PCRE2_ERROR_UTF8_ERR20 = -(22);
+  PCRE2_ERROR_UTF8_ERR21 = -(23);
+  PCRE2_ERROR_UTF16_ERR1 = -(24);
+  PCRE2_ERROR_UTF16_ERR2 = -(25);
+  PCRE2_ERROR_UTF16_ERR3 = -(26);
+  PCRE2_ERROR_UTF32_ERR1 = -(27);
+  PCRE2_ERROR_UTF32_ERR2 = -(28);
+  PCRE2_ERROR_BADDATA = -(29);
+  PCRE2_ERROR_MIXEDTABLES = -(30);
+  PCRE2_ERROR_BADMAGIC = -(31);
+  PCRE2_ERROR_BADMODE = -(32);
+  PCRE2_ERROR_BADOFFSET = -(33);
+  PCRE2_ERROR_BADOPTION = -(34);
+  PCRE2_ERROR_BADREPLACEMENT = -(35);
+  PCRE2_ERROR_BADUTFOFFSET = -(36);
+  PCRE2_ERROR_CALLOUT = -(37);
+  PCRE2_ERROR_DFA_BADRESTART = -(38);
+  PCRE2_ERROR_DFA_RECURSE = -(39);
+  PCRE2_ERROR_DFA_UCOND = -(40);
+  PCRE2_ERROR_DFA_UFUNC = -(41);
+  PCRE2_ERROR_DFA_UITEM = -(42);
+  PCRE2_ERROR_DFA_WSSIZE = -(43);
+  PCRE2_ERROR_INTERNAL = -(44);
+  PCRE2_ERROR_JIT_BADOPTION = -(45);
+  PCRE2_ERROR_JIT_STACKLIMIT = -(46);
+  PCRE2_ERROR_MATCHLIMIT = -(47);
+  PCRE2_ERROR_NOMEMORY = -(48);
+  PCRE2_ERROR_NOSUBSTRING = -(49);
+  PCRE2_ERROR_NOUNIQUESUBSTRING = -(50);
+  PCRE2_ERROR_NULL = -(51);
+  PCRE2_ERROR_RECURSELOOP = -(52);
+  PCRE2_ERROR_DEPTHLIMIT = -(53);
+  PCRE2_ERROR_RECURSIONLIMIT = -(53);
+  PCRE2_ERROR_UNAVAILABLE = -(54);
+  PCRE2_ERROR_UNSET = -(55);
+  PCRE2_ERROR_BADOFFSETLIMIT = -(56);
+  PCRE2_ERROR_BADREPESCAPE = -(57);
+  PCRE2_ERROR_REPMISSINGBRACE = -(58);
+  PCRE2_ERROR_BADSUBSTITUTION = -(59);
+  PCRE2_ERROR_BADSUBSPATTERN = -(60);
+  PCRE2_ERROR_TOOMANYREPLACE = -(61);
+  PCRE2_ERROR_BADSERIALIZEDDATA = -(62);
+  PCRE2_ERROR_HEAPLIMIT = -(63);
+  PCRE2_ERROR_CONVERT_SYNTAX = -(64);
+  PCRE2_ERROR_INTERNAL_DUPMATCH = -(65);
+  PCRE2_ERROR_DFA_UINVALID_UTF = -(66);
+
+  PCRE2_INFO_ALLOPTIONS = 0;
+  PCRE2_INFO_ARGOPTIONS = 1;
+  PCRE2_INFO_BACKREFMAX = 2;
+  PCRE2_INFO_BSR = 3;
+  PCRE2_INFO_CAPTURECOUNT = 4;
+  PCRE2_INFO_FIRSTCODEUNIT = 5;
+  PCRE2_INFO_FIRSTCODETYPE = 6;
+  PCRE2_INFO_FIRSTBITMAP = 7;
+  PCRE2_INFO_HASCRORLF = 8;
+  PCRE2_INFO_JCHANGED = 9;
+  PCRE2_INFO_JITSIZE = 10;
+  PCRE2_INFO_LASTCODEUNIT = 11;
+  PCRE2_INFO_LASTCODETYPE = 12;
+  PCRE2_INFO_MATCHEMPTY = 13;
+  PCRE2_INFO_MATCHLIMIT = 14;
+  PCRE2_INFO_MAXLOOKBEHIND = 15;
+  PCRE2_INFO_MINLENGTH = 16;
+  PCRE2_INFO_NAMECOUNT = 17;
+  PCRE2_INFO_NAMEENTRYSIZE = 18;
+  PCRE2_INFO_NAMETABLE = 19;
+  PCRE2_INFO_NEWLINE = 20;
+  PCRE2_INFO_DEPTHLIMIT = 21;
+  PCRE2_INFO_RECURSIONLIMIT = 21;
+  PCRE2_INFO_SIZE = 22;
+  PCRE2_INFO_HASBACKSLASHC = 23;
+  PCRE2_INFO_FRAMESIZE = 24;
+  PCRE2_INFO_HEAPLIMIT = 25;
+  PCRE2_INFO_EXTRAOPTIONS = 26;
+
+  PCRE2_CONFIG_BSR = 0;
+  PCRE2_CONFIG_JIT = 1;
+  PCRE2_CONFIG_JITTARGET = 2;
+  PCRE2_CONFIG_LINKSIZE = 3;
+  PCRE2_CONFIG_MATCHLIMIT = 4;
+  PCRE2_CONFIG_NEWLINE = 5;
+  PCRE2_CONFIG_PARENSLIMIT = 6;
+  PCRE2_CONFIG_DEPTHLIMIT = 7;
+  PCRE2_CONFIG_RECURSIONLIMIT = 7;
+  PCRE2_CONFIG_STACKRECURSE = 8;
+  PCRE2_CONFIG_UNICODE = 9;
+  PCRE2_CONFIG_UNICODE_VERSION = 10;
+  PCRE2_CONFIG_VERSION = 11;
+  PCRE2_CONFIG_HEAPLIMIT = 12;
+  PCRE2_CONFIG_NEVER_BACKSLASH_C = 13;
+  PCRE2_CONFIG_COMPILED_WIDTHS = 14;
+  PCRE2_CONFIG_TABLES_LENGTH = 15;
+