pkgsrc-Changes archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

CVS commit: pkgsrc/graphics/camlimages



Module Name:    pkgsrc
Committed By:   dholland
Date:           Sun Dec 26 05:28:23 UTC 2021

Modified Files:
        pkgsrc/graphics/camlimages: distinfo
        pkgsrc/graphics/camlimages/patches: patch-src_gifread.c
            patch-src_gifwrite.c patch-src_jpegread.c patch-src_tiffread.c
            patch-src_tiffwrite.c
Added Files:
        pkgsrc/graphics/camlimages/patches: patch-examples_crop_crop.ml
            patch-examples_liv_icon.ml patch-examples_liv_livsh.ml
            patch-examples_liv_livshtype.ml patch-examples_liv_scandir.ml
            patch-examples_tiffps_tiffps.ml patch-src_bitmap.ml
            patch-src_bitmap.mli patch-src_bmp.ml patch-src_bmp.mli
            patch-src_cmyk32.ml patch-src_cmyk32.mli patch-src_genimage.ml
            patch-src_gif.ml patch-src_gif.mli patch-src_image__intf.mli
            patch-src_imagegdk.ml patch-src_images.ml patch-src_index16.ml
            patch-src_index16.mli patch-src_index8.ml patch-src_index8.mli
            patch-src_jpeg.ml patch-src_jpeg.mli patch-src_jpegwrite.c
            patch-src_mstring.ml patch-src_oImages.ml patch-src_oImages.mli
            patch-src_png.ml patch-src_rgb24.ml patch-src_rgb24.mli
            patch-src_rgba32.ml patch-src_rgba32.mli patch-src_tiff.ml
            patch-src_tiff.mli patch-src_units.ml patch-src_xpm.ml
            patch-src_xvthumb.ml

Log Message:
graphics/camlimages: make it build again

Hasn't in a long time, so no PKGREVISION bump (it's at 96!)

It is fairly likely that these changes and/or OCaml internal changes
regarding immutable strings have changed the behavior if you abuse
internal interfaces or try to share graphics memory with the library
and scribble on it. Don't do that.

There are probably more data copies as well (meaning "slow") but I've
tried to avoid that as much as possible.


To generate a diff of this commit:
cvs rdiff -u -r1.18 -r1.19 pkgsrc/graphics/camlimages/distinfo
cvs rdiff -u -r0 -r1.1 \
    pkgsrc/graphics/camlimages/patches/patch-examples_crop_crop.ml \
    pkgsrc/graphics/camlimages/patches/patch-examples_liv_icon.ml \
    pkgsrc/graphics/camlimages/patches/patch-examples_liv_livsh.ml \
    pkgsrc/graphics/camlimages/patches/patch-examples_liv_livshtype.ml \
    pkgsrc/graphics/camlimages/patches/patch-examples_liv_scandir.ml \
    pkgsrc/graphics/camlimages/patches/patch-examples_tiffps_tiffps.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_bitmap.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_bitmap.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_bmp.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_bmp.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_genimage.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_gif.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_gif.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_image__intf.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_imagegdk.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_images.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_index16.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_index16.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_index8.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_index8.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_jpeg.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_jpeg.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_jpegwrite.c \
    pkgsrc/graphics/camlimages/patches/patch-src_mstring.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_oImages.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_oImages.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_png.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_rgb24.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_rgb24.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_rgba32.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_rgba32.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_tiff.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_tiff.mli \
    pkgsrc/graphics/camlimages/patches/patch-src_units.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_xpm.ml \
    pkgsrc/graphics/camlimages/patches/patch-src_xvthumb.ml
cvs rdiff -u -r1.2 -r1.3 \
    pkgsrc/graphics/camlimages/patches/patch-src_gifread.c \
    pkgsrc/graphics/camlimages/patches/patch-src_gifwrite.c \
    pkgsrc/graphics/camlimages/patches/patch-src_jpegread.c \
    pkgsrc/graphics/camlimages/patches/patch-src_tiffread.c \
    pkgsrc/graphics/camlimages/patches/patch-src_tiffwrite.c

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: pkgsrc/graphics/camlimages/distinfo
diff -u pkgsrc/graphics/camlimages/distinfo:1.18 pkgsrc/graphics/camlimages/distinfo:1.19
--- pkgsrc/graphics/camlimages/distinfo:1.18    Tue Oct 26 10:46:01 2021
+++ pkgsrc/graphics/camlimages/distinfo Sun Dec 26 05:28:23 2021
@@ -1,13 +1,51 @@
-$NetBSD: distinfo,v 1.18 2021/10/26 10:46:01 nia Exp $
+$NetBSD: distinfo,v 1.19 2021/12/26 05:28:23 dholland Exp $
 
 BLAKE2s (camlimages-4.0.1a/v4.0.1.tar.gz) = 0d8e3e7a10f89ff6afd5161a840ea9951a563daf8388f2717d2f75257b6276d4
 SHA512 (camlimages-4.0.1a/v4.0.1.tar.gz) = c4e2a816911ed128c0414308d1ace914bbb51e40b6d70a3c492690b38c860f79e3e01efa3f1be7d57654c78f8acca6f30bffb9e6b8fd423d1d36d6a477d0fd8d
 Size (camlimages-4.0.1a/v4.0.1.tar.gz) = 2190274 bytes
 SHA1 (patch-OMakefile) = f650eca9bf8edbc64f9f5352718ee2046c368667
-SHA1 (patch-src_gifread.c) = 63aac1a76e809676f0000f37af63c79c4edbe316
-SHA1 (patch-src_gifwrite.c) = ab92107467b059d9541edacf60a5f73ed71fd687
-SHA1 (patch-src_jpegread.c) = 2b32040ce34218437bb4947d8a87fe2b840223b4
+SHA1 (patch-examples_crop_crop.ml) = 52d7fc9c39c394ecac22fe3d401aaef73c64b50d
+SHA1 (patch-examples_liv_icon.ml) = 29e1a5b7325f0b468dc76291563697ae301de664
+SHA1 (patch-examples_liv_livsh.ml) = b804ef21be7e55b3c63011f614cc1e3e6902cb16
+SHA1 (patch-examples_liv_livshtype.ml) = 9b1ef9063955b243162336b527c94cf74d9c46cc
+SHA1 (patch-examples_liv_scandir.ml) = 7579833c57347acd3520a4905696e0a6edbaf7ab
+SHA1 (patch-examples_tiffps_tiffps.ml) = ed9b8cafbd4ebd7a09270c5983f01a683da151a3
+SHA1 (patch-src_bitmap.ml) = 763d7e6ac20142e4bb97b7e154bc1eebc4acf8c8
+SHA1 (patch-src_bitmap.mli) = d1e3cb5521028d18992be2a581692062b69e3765
+SHA1 (patch-src_bmp.ml) = e2c18f97e675b5c51b783fbc8e585b9549e09d8c
+SHA1 (patch-src_bmp.mli) = b56b5a6e7ed02714fe530f31d10bb2ac8a06eb44
+SHA1 (patch-src_cmyk32.ml) = 2cbc055ee1bad6f8d3789f32f8ff5c47f0c22dfc
+SHA1 (patch-src_cmyk32.mli) = 4ba75d4520538581882b832c09a1c708a904719d
+SHA1 (patch-src_genimage.ml) = d9de0188a077f89045c819e8f638db7a28c0449f
+SHA1 (patch-src_gif.ml) = 05c3970e16de2dbca0fb35a5e778d3a4fd91b92e
+SHA1 (patch-src_gif.mli) = 07c8422510de110f22d27edae20228780f57e532
+SHA1 (patch-src_gifread.c) = 917730ca374bcf258cd86e2d1608d22467ac3ec2
+SHA1 (patch-src_gifwrite.c) = 555f5221ffa3a5e3bd5f59b1e6e3cc3f6b6ac80f
+SHA1 (patch-src_image__intf.mli) = 784ada5f15c0a13c367f98e9e01275719a67012f
+SHA1 (patch-src_imagegdk.ml) = 1a3e79fb72b475985dd9460870bceb6b20d4d67e
+SHA1 (patch-src_images.ml) = 95182ba6a8d7184ed4e6937a3c584406bea553d8
+SHA1 (patch-src_index16.ml) = dbef2ab65fc3b1c6a4b8a982c7f2767507c16d42
+SHA1 (patch-src_index16.mli) = 6fe184ae5c65f1438f8e8317cc9162e3b27eb173
+SHA1 (patch-src_index8.ml) = 298c22edebcc40db3f48f832482af3a910a69fef
+SHA1 (patch-src_index8.mli) = 3d6121e5758aeedef6aa39ecb717669cc85d35cc
+SHA1 (patch-src_jpeg.ml) = 4b87eb4ffc0b41e3bcac077e436f4629af79a885
+SHA1 (patch-src_jpeg.mli) = 0541546c398bbf54a04cab41fe27ca804407301e
+SHA1 (patch-src_jpegread.c) = a0cf27be87c288bd990d8060ab56974064337e46
+SHA1 (patch-src_jpegwrite.c) = acafaace41c8b69d6f0f71e7e0ebf3311dbf8e33
+SHA1 (patch-src_mstring.ml) = 84ec525bd572ea1a5d44869c4f5a4afc6ae94d2e
+SHA1 (patch-src_oImages.ml) = 40d0b13cfa54647da850172142c054576a8ce073
+SHA1 (patch-src_oImages.mli) = 0b6290c409eadf60ee3dcece8895dbab90ae36be
+SHA1 (patch-src_png.ml) = 613dc0b5bace73423f3ccad0f393881220fcc877
 SHA1 (patch-src_pngread.c) = 00d753b8570b5ff9ffa71e6e62328496b03f9654
 SHA1 (patch-src_pngwrite.c) = 4df4f69851769e0eefc2249a30ac8dd53aa8d755
-SHA1 (patch-src_tiffread.c) = 4dab0fe8da42fe7d0720d5edddf45743c7fa41fd
-SHA1 (patch-src_tiffwrite.c) = 2bc3de2b56a8f8d46fac3ac8d7c1b9ae9c4bd52c
+SHA1 (patch-src_rgb24.ml) = 9b30ac9f92992e30e0dc33fe4f0b09fffc4504d5
+SHA1 (patch-src_rgb24.mli) = 8a9e765a8b9c787796c7f7f3effc9d7fe542c32b
+SHA1 (patch-src_rgba32.ml) = 00ad9906236c1f85e79d26cab68f76f541f9aba5
+SHA1 (patch-src_rgba32.mli) = 4cb8e6b36d463c019299a9553a5622e6a4f22edf
+SHA1 (patch-src_tiff.ml) = a668e0a414121ba566d270eede9c4a0213419d54
+SHA1 (patch-src_tiff.mli) = 51938d692d0589134c9ef5bdd4ca25013fc74406
+SHA1 (patch-src_tiffread.c) = 42e5891b57bf46705a597d1515016e6fe84e65fe
+SHA1 (patch-src_tiffwrite.c) = c35f55594ab56373dd0f00d55c125209f7a88377
+SHA1 (patch-src_units.ml) = 65f6b69092f2618756848ad7291432c84a230bce
+SHA1 (patch-src_xpm.ml) = f5eee2983770100f1f7999c1c2fbb6e1155b83cf
+SHA1 (patch-src_xvthumb.ml) = b1142f4aae2e1692ec4b6fe25633fc84aeff604f

Index: pkgsrc/graphics/camlimages/patches/patch-src_gifread.c
diff -u pkgsrc/graphics/camlimages/patches/patch-src_gifread.c:1.2 pkgsrc/graphics/camlimages/patches/patch-src_gifread.c:1.3
--- pkgsrc/graphics/camlimages/patches/patch-src_gifread.c:1.2  Sat May 24 04:05:24 2014
+++ pkgsrc/graphics/camlimages/patches/patch-src_gifread.c      Sun Dec 26 05:28:23 2021
@@ -1,12 +1,26 @@
-$NetBSD: patch-src_gifread.c,v 1.2 2014/05/24 04:05:24 obache Exp $
+$NetBSD: patch-src_gifread.c,v 1.3 2021/12/26 05:28:23 dholland Exp $
 
-* DGifOpenFileName API change for giflib-5
-* DGifCloseFile API change for giflib-5.1
-* PrintGifError API removal for giflib-4.2.0
+- DGifOpenFileName API change for giflib-5
+- DGifCloseFile API change for giflib-5.1
+- PrintGifError API removal for giflib-4.2.0
+- Update for immutable OCaml strings
 
 --- src/gifread.c.orig 2011-06-22 18:04:32.000000000 +0000
 +++ src/gifread.c
-@@ -140,7 +140,7 @@ value dGifOpenFileName( value name )
+@@ -20,6 +20,12 @@
+ #include <caml/memory.h>
+ #include <caml/fail.h>
+ 
++/*
++ * For future-proofing: currently in the ocaml FFI you use
++ * alloc_string for Bytes.t but that could change...
++ */
++#define alloc_bytes alloc_string
++
+ #include "oversized.h"
+ 
+ #include <stdio.h>
+@@ -140,7 +146,7 @@ value dGifOpenFileName( value name )
    GifFileType *GifFile;
    int i;
  
@@ -15,7 +29,7 @@ $NetBSD: patch-src_gifread.c,v 1.2 2014/
      failwith("DGifOpenFileName");
    }
  
-@@ -161,7 +161,7 @@ value dGifCloseFile( value hdl )
+@@ -161,7 +167,7 @@ value dGifCloseFile( value hdl )
       segmentation faults */
    ((GifFileType *)hdl)->Image.ColorMap = NULL; 
  
@@ -24,11 +38,27 @@ $NetBSD: patch-src_gifread.c,v 1.2 2014/
    CAMLreturn(Val_unit);
  }
  
-@@ -200,7 +200,6 @@ value dGifGetLine( value hdl )
+@@ -196,11 +202,10 @@ value dGifGetLine( value hdl )
+   if( oversized( GifFile->Image.Width, sizeof(GifPixelType) ) ){
+     failwith_oversized("gif");
+   }
+-  buf = alloc_string( GifFile->Image.Width * sizeof(GifPixelType) ); 
++  buf = alloc_bytes( GifFile->Image.Width * sizeof(GifPixelType) ); 
  
-   if( DGifGetLine(GifFile, String_val(buf), GifFile->Image.Width ) 
+-  if( DGifGetLine(GifFile, String_val(buf), GifFile->Image.Width ) 
++  if( DGifGetLine(GifFile, Bytes_val(buf), GifFile->Image.Width ) 
        == GIF_ERROR ){
 -    PrintGifError ();
      failwith("DGifGetLine");
    }
    CAMLreturn(buf);
+@@ -223,8 +228,7 @@ value dGifGetExtension( value hdl )
+   }
+ 
+   while( extData != NULL ){
+-    ext= alloc_string(extData[0]);
+-    memcpy(String_val(ext), &extData[1], extData[0]);
++    ext= caml_alloc_initialized_string(extData[0], &extData[1]);
+     newres = alloc_small(2,0);
+     Field(newres, 0)= ext;
+     Field(newres, 1)= exts;
Index: pkgsrc/graphics/camlimages/patches/patch-src_gifwrite.c
diff -u pkgsrc/graphics/camlimages/patches/patch-src_gifwrite.c:1.2 pkgsrc/graphics/camlimages/patches/patch-src_gifwrite.c:1.3
--- pkgsrc/graphics/camlimages/patches/patch-src_gifwrite.c:1.2 Sat May 24 04:05:24 2014
+++ pkgsrc/graphics/camlimages/patches/patch-src_gifwrite.c     Sun Dec 26 05:28:23 2021
@@ -1,13 +1,25 @@
-$NetBSD: patch-src_gifwrite.c,v 1.2 2014/05/24 04:05:24 obache Exp $
+$NetBSD: patch-src_gifwrite.c,v 1.3 2021/12/26 05:28:23 dholland Exp $
 
-* MakeMapObject API rename for giflib-5
-* DGifOpenFileName API change for giflib-5
-* DGifCloseFile API change for giflib-5.1
-* PrintGifError API removal for giflib-4.2.0
+- MakeMapObject API rename for giflib-5
+- DGifOpenFileName API change for giflib-5
+- DGifCloseFile API change for giflib-5.1
+- PrintGifError API removal for giflib-4.2.0
+- Don't use CAMLreturn for functions that aren't OCaml interfaces.
+- Cast away const where OCaml provides it and giflib doesn't accept it.
+- Update for OCaml immutable strings.
 
 --- src/gifwrite.c.orig        2011-06-22 18:04:32.000000000 +0000
 +++ src/gifwrite.c
-@@ -52,7 +52,7 @@ ColorMapObject *ColorMapObject_val( valu
+@@ -44,7 +44,7 @@ ColorMapObject *ColorMapObject_val( valu
+   int i;
+   ColorMapObject *cmapobj;
+ 
+-  if( cmap == Atom(0) ){ CAMLreturn(NULL); } 
++  if( cmap == Atom(0) ){ return NULL; } 
+ 
+   len = Wosize_val(cmap);
+ 
+@@ -52,13 +52,13 @@ ColorMapObject *ColorMapObject_val( valu
  fprintf(stderr, "Creating map with length = %d ...\n", len);
  fflush(stderr);
  */
@@ -16,6 +28,13 @@ $NetBSD: patch-src_gifwrite.c,v 1.2 2014
    for(i=0; i< len; i++){
      cmapobj->Colors[i].Red   = Int_val(Field(Field(cmap,i),0));
      cmapobj->Colors[i].Green = Int_val(Field(Field(cmap,i),1));
+     cmapobj->Colors[i].Blue  = Int_val(Field(Field(cmap,i),2));
+   }
+-  CAMLreturn(cmapobj); 
++  return cmapobj;
+ }
+ 
+ value eGifOpenFileName( name )
 @@ -68,7 +68,7 @@ value eGifOpenFileName( name )
  
    GifFileType *GifFileOut;
@@ -34,9 +53,12 @@ $NetBSD: patch-src_gifwrite.c,v 1.2 2014
    CAMLreturn(Val_unit);
  }
  
-@@ -133,7 +133,6 @@ value eGifPutLine( value oc, value buf )
+@@ -131,9 +131,8 @@ value eGifPutLine( value oc, value buf )
+ 
+   GifFileType *GifFileOut = (GifFileType*) oc;
  
-   if ( EGifPutLine(GifFileOut, String_val(buf), GifFileOut->Image.Width) 
+-  if ( EGifPutLine(GifFileOut, String_val(buf), GifFileOut->Image.Width) 
++  if ( EGifPutLine(GifFileOut, (char *)String_val(buf), GifFileOut->Image.Width) 
         == GIF_ERROR ){
 -    PrintGifError ();
      failwith("EGifPutLine");
Index: pkgsrc/graphics/camlimages/patches/patch-src_jpegread.c
diff -u pkgsrc/graphics/camlimages/patches/patch-src_jpegread.c:1.2 pkgsrc/graphics/camlimages/patches/patch-src_jpegread.c:1.3
--- pkgsrc/graphics/camlimages/patches/patch-src_jpegread.c:1.2 Sun Sep 18 05:48:59 2016
+++ pkgsrc/graphics/camlimages/patches/patch-src_jpegread.c     Sun Dec 26 05:28:23 2021
@@ -1,10 +1,73 @@
-$NetBSD: patch-src_jpegread.c,v 1.2 2016/09/18 05:48:59 dholland Exp $
+$NetBSD: patch-src_jpegread.c,v 1.3 2021/12/26 05:28:23 dholland Exp $
 
-Make clang happy with proper return value
+Use const.
+
+Update for OCaml immutable strings.
 
 --- src/jpegread.c.orig        2011-06-22 18:04:32.000000000 +0000
 +++ src/jpegread.c
-@@ -417,7 +417,7 @@ value read_jpeg_scanlines( value jpegh, 
+@@ -23,6 +23,12 @@
+ #include <caml/memory.h>
+ #include <caml/fail.h>
+ 
++/*
++ * For future-proofing: currently in the ocaml FFI you use
++ * alloc_string for Bytes.t but that could change...
++ */
++#define alloc_bytes alloc_string
++
+ #include "oversized.h"
+ 
+ #include <stdio.h>
+@@ -76,7 +82,7 @@ read_JPEG_file (value name)
+   CAMLparam1(name);
+   CAMLlocal1(res);
+ 
+-  char *filename;
++  const char *filename;
+   /* This struct contains the JPEG decompression parameters and pointers to
+    * working space (which is allocated as needed by the JPEG library).
+    */
+@@ -198,9 +204,9 @@ read_JPEG_file (value name)
+     CAMLlocalN(r,3);
+     r[0] = Val_int(cinfo.output_width);
+     r[1] = Val_int(cinfo.output_height);
+-    r[2] = alloc_string ( row_stride * cinfo.output_height );
++    r[2] = alloc_bytes ( row_stride * cinfo.output_height );
+     for(i=0; i<cinfo.output_height; i++){
+-      memcpy( String_val(r[2]) + i * row_stride, 
++      memcpy( Bytes_val(r[2]) + i * row_stride, 
+              buffer[i], row_stride);
+     }
+     res = alloc_tuple(3);
+@@ -253,7 +259,7 @@ value open_jpeg_file_for_read( name )
+   CAMLparam1(name);
+   CAMLlocal1(res);
+ 
+-  char *filename;
++  const char *filename;
+   /* This struct contains the JPEG decompression parameters and pointers to
+    * working space (which is allocated as needed by the JPEG library).
+    */
+@@ -395,7 +401,7 @@ value jpegh, offset, buf;
+   JSAMPROW row[1];
+ 
+   cinfop = (struct jpeg_decompress_struct *) Field( jpegh, 0 );
+-  row[0] = String_val( buf ) + Int_val( offset );
++  row[0] = Bytes_val( buf ) + Int_val( offset );
+   jpeg_read_scanlines( cinfop, row, 1 );
+ 
+   CAMLreturn(Val_unit);
+@@ -409,7 +415,7 @@ value read_jpeg_scanlines( value jpegh, 
+   JSAMPROW row[1];
+   int clines = Int_val(lines);
+   int i;
+-  row[0] = String_val(buf) + Int_val(offset);
++  row[0] = Bytes_val(buf) + Int_val(offset);
+   cinfop = (struct jpeg_decompress_struct *) Field( jpegh, 0 );
+   // width is NOT image_width since we may have scale_denom <> 1
+   int scanline_bytes = cinfop->output_width * 3; // no padding (size 3 is fixed? )
+@@ -417,7 +423,7 @@ value read_jpeg_scanlines( value jpegh, 
      jpeg_read_scanlines( cinfop, row, 1 );
      row[0] += scanline_bytes;
    }
Index: pkgsrc/graphics/camlimages/patches/patch-src_tiffread.c
diff -u pkgsrc/graphics/camlimages/patches/patch-src_tiffread.c:1.2 pkgsrc/graphics/camlimages/patches/patch-src_tiffread.c:1.3
--- pkgsrc/graphics/camlimages/patches/patch-src_tiffread.c:1.2 Sun Jul 29 12:52:55 2012
+++ pkgsrc/graphics/camlimages/patches/patch-src_tiffread.c     Sun Dec 26 05:28:23 2021
@@ -1,33 +1,69 @@
-$NetBSD: patch-src_tiffread.c,v 1.2 2012/07/29 12:52:55 marino Exp $
+$NetBSD: patch-src_tiffread.c,v 1.3 2021/12/26 05:28:23 dholland Exp $
 
-Both ocaml/caml/config.h and tiff.h define int32, uint32, etc.
-The workaround of this name polution is to intentionally overwrite the
-first caml definition with a garbage macro before tiff.h is included and
-then unset it after the include.  After tiff version 4.0.1, the same hack
-has to be applied to 64-bit types.  Unlike tiffwrite.c, tiffread.c forgot
-to unset the bogus definitions.  The uint16 and uint32 then has to be
-redefined correctly.  (ugly hack)
+- ocaml/caml/compatibility.h defines int16 and uint16, which break tiff.
+They're not needed, so clear them out. (There are no more int32/uint32
+defines, so that logic can be removed.)
+
+- tiff doesn't use "uint32" and "uint16" either any more, so use the
+standard names.
+
+- Use const.
+
+- Update for OCaml immutable strings.
 
 --- src/tiffread.c.orig        2011-06-22 18:04:32.000000000 +0000
 +++ src/tiffread.c
-@@ -28,9 +28,20 @@
- #define uint16 uint16tiff
- #define int32 int32tiff
- #define uint32 uint32tiff
-+#define int64 int64tiff
-+#define uint64 uint64tiff
+@@ -23,11 +23,9 @@
  
- #include <tiffio.h>
+ #include "oversized.h"
  
+-/* These are defined in caml/config.h */
+-#define int16 int16tiff
+-#define uint16 uint16tiff
+-#define int32 int32tiff
+-#define uint32 uint32tiff
++/* These are defined in caml/compatibility.h and break tiff */
 +#undef int16
 +#undef uint16
-+#undef int32
-+#undef uint32
-+#undef int64
-+#undef uint64
-+#define uint16 uint16_t
-+#define uint32 uint32_t
-+
- extern value *imglib_error;
  
- value open_tiff_file_for_read( name )
+ #include <tiffio.h>
+ 
+@@ -40,22 +38,22 @@ value open_tiff_file_for_read( name )
+   CAMLlocal1(res);
+   CAMLlocalN(r,5);
+ 
+-  char *filename; 
++  const char *filename;
+   TIFF* tif;
+   
+   filename = String_val( name );
+   
+   tif = TIFFOpen(filename, "r");
+   if (tif) {
+-    uint32 imagelength;
+-    uint32 imagewidth;
+-    uint16 imagesample;
+-    uint16 imagebits;
++    uint32_t imagelength;
++    uint32_t imagewidth;
++    uint16_t imagesample;
++    uint16_t imagebits;
+     tdata_t buf;
+     int i;
+-    uint16 runit;
++    uint16_t runit;
+     float xres, yres;
+-    uint16 photometric;
++    uint16_t photometric;
+ 
+     TIFFGetField(tif, TIFFTAG_IMAGELENGTH, &imagelength);
+     TIFFGetField(tif, TIFFTAG_IMAGEWIDTH, &imagewidth);
+@@ -114,7 +112,7 @@ value read_tiff_scanline( tiffh, buf, ro
+      value row;
+ {
+   CAMLparam3(tiffh,buf,row);
+-  TIFFReadScanline((TIFF*)tiffh, String_val(buf), Int_val(row), 0);
++  TIFFReadScanline((TIFF*)tiffh, Bytes_val(buf), Int_val(row), 0);
+   CAMLreturn(Val_unit);
+ }
+ 
Index: pkgsrc/graphics/camlimages/patches/patch-src_tiffwrite.c
diff -u pkgsrc/graphics/camlimages/patches/patch-src_tiffwrite.c:1.2 pkgsrc/graphics/camlimages/patches/patch-src_tiffwrite.c:1.3
--- pkgsrc/graphics/camlimages/patches/patch-src_tiffwrite.c:1.2        Sun Sep 18 05:46:31 2016
+++ pkgsrc/graphics/camlimages/patches/patch-src_tiffwrite.c    Sun Dec 26 05:28:23 2021
@@ -1,36 +1,38 @@
-$NetBSD: patch-src_tiffwrite.c,v 1.2 2016/09/18 05:46:31 dholland Exp $
+$NetBSD: patch-src_tiffwrite.c,v 1.3 2021/12/26 05:28:23 dholland Exp $
 
- - Both ocaml/caml/config.h and tiff.h define int32, uint32, etc.
-The workaround of this name polution is to intentionally overwrite the
-first caml definition with a garbage macro before tiff.h is included and
-then unset it after the include.  After tiff version 4.0.1, the same hack
-has to be applied to 64-bit types.
+- ocaml/caml/compatibility.h defines int16 and uint16, which break tiff.
+They're not needed, so clear them out. (There are no more int32/uint32
+defines, so that logic can be removed.)
 
- - As of some newer ocaml there's no "uint32", only "uint32_t". The
-first two hunks of this patch are probably no longer necessary.
+- tiff uses uint32_t instead of its own uint32 these days.
 
+- Cast away const where ocaml provides const and tiff doesn't accept it.
 
 --- src/tiffwrite.c.orig       2011-06-22 18:04:32.000000000 +0000
 +++ src/tiffwrite.c
-@@ -25,6 +25,8 @@
- #define uint16 uint16tiff
- #define int32 int32tiff
- #define uint32 uint32tiff
-+#define int64 int64tiff
-+#define uint64 uint64tiff
+@@ -20,18 +20,11 @@
+ #include <caml/memory.h>
+ #include <caml/fail.h>
  
- #include <tiffio.h>
- 
-@@ -32,6 +34,8 @@
+-/* These are defined in caml/config.h */
+-#define int16 int16tiff
+-#define uint16 uint16tiff
+-#define int32 int32tiff
+-#define uint32 uint32tiff
+-
+-#include <tiffio.h>
+-
++/* These are defined in caml/compatibility.h and break tiff */
+ #undef int16
  #undef uint16
- #undef int32
- #undef uint32
-+#undef int64
-+#undef uint64
+-#undef int32
+-#undef uint32
++
++#include <tiffio.h>
  
  extern value *imglib_error;
  
-@@ -56,8 +60,8 @@ value open_tiff_file_for_write( value fi
+@@ -56,8 +49,8 @@ value open_tiff_file_for_write( value fi
      /* Resolution */
      /* FillOrder */
      
@@ -41,3 +43,11 @@ first two hunks of this patch are probab
      TIFFSetField(tif, TIFFTAG_ORIENTATION, ORIENTATION_TOPLEFT);
      TIFFSetField(tif, TIFFTAG_SAMPLESPERPIXEL, 3);
      TIFFSetField(tif, TIFFTAG_BITSPERSAMPLE, 8);
+@@ -83,6 +76,6 @@ value write_tiff_scanline( tiffh, buf, r
+      value row;
+ {
+   CAMLparam3(tiffh,buf,row);
+-  TIFFWriteScanline((TIFF*)tiffh, String_val(buf), Int_val(row), 0);
++  TIFFWriteScanline((TIFF*)tiffh, (char *)String_val(buf), Int_val(row), 0);
+   CAMLreturn(Val_unit);
+ }

Added files:

Index: pkgsrc/graphics/camlimages/patches/patch-examples_crop_crop.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-examples_crop_crop.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-examples_crop_crop.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-examples_crop_crop.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- examples/crop/crop.ml~     2011-06-22 18:04:32.000000000 +0000
++++ examples/crop/crop.ml
+@@ -46,7 +46,7 @@ let edge edgename img24 =
+     match edgename with
+     | Some _ ->
+         Some (new rgb24_with img24#width img24#height
+-                [] (String.copy img24#dump))
++                [] img24#dump)
+     | None -> None in
+   let edge = Array.init img24#width (fun _ -> Array.create img24#height 0) in
+ 
Index: pkgsrc/graphics/camlimages/patches/patch-examples_liv_icon.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-examples_liv_icon.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-examples_liv_icon.ml       Sun Dec 26 05:28:23 2021
@@ -0,0 +1,17 @@
+$NetBSD: patch-examples_liv_icon.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Use "Stdlib" instead of "Pervasives".
+
+--- examples/liv/icon.ml~      2011-06-22 18:04:32.000000000 +0000
++++ examples/liv/icon.ml
+@@ -98,8 +98,8 @@ let create_livthumb name =
+       | Rgb24 i -> i
+       | _ -> assert false in
+     img#resize None
+-      (Pervasives.truncate (float w *. ratio))
+-      (Pervasives.truncate (float h *. ratio)) in
++      (Stdlib.truncate (float w *. ratio))
++      (Stdlib.truncate (float h *. ratio)) in
+   img#save thumbpath (Some Jpeg) [Save_Quality 75];
+   img#destroy;;
+ 
Index: pkgsrc/graphics/camlimages/patches/patch-examples_liv_livsh.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-examples_liv_livsh.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-examples_liv_livsh.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,21 @@
+$NetBSD: patch-examples_liv_livsh.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Sort.list is so old it's not even in the deprecations section of the
+manual any more. Use List.sort.
+
+--- examples/liv/livsh.ml~     2011-06-22 18:04:32.000000000 +0000
++++ examples/liv/livsh.ml
+@@ -365,10 +365,10 @@ class livsh init_dir func =
+         | "special", "lnkdir" -> 0
+         | "special", _ -> 10
+         | _ -> 100 in
+-      if typval a = typval b then a#name < b#name
+-      else typval a < typval b in
++      if typval a = typval b then compare a#name b#name
++      else compare (typval a) (typval b) in
+ 
+-    items <-  Sort.list sortf items_unsort;
++    items <-  List.sort sortf items_unsort;
+     self#set_text "";
+     self#deactivate ()
+ 
Index: pkgsrc/graphics/camlimages/patches/patch-examples_liv_livshtype.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-examples_liv_livshtype.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-examples_liv_livshtype.ml  Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-examples_liv_livshtype.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Silence nuisance warning about lowercase.
+
+--- examples/liv/livshtype.ml~ 2011-06-22 18:04:32.000000000 +0000
++++ examples/liv/livshtype.ml
+@@ -119,7 +119,7 @@ let guess link_as_link f =
+       try from_header f
+       with
+       | _ ->
+-        Hashtbl.find suffixes (String.lowercase (snd (Livmisc.get_extension f)))
++        Hashtbl.find suffixes (String.lowercase_ascii (snd (Livmisc.get_extension f)))
+     end;;
+ 
+ let guess = guess false
Index: pkgsrc/graphics/camlimages/patches/patch-examples_liv_scandir.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-examples_liv_scandir.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-examples_liv_scandir.ml    Sun Dec 26 05:28:23 2021
@@ -0,0 +1,16 @@
+$NetBSD: patch-examples_liv_scandir.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Sort.list is so old it's not even in the deprecations section of the
+manual any more. Use List.sort.
+
+--- examples/liv/scandir.ml~   2011-06-22 18:04:32.000000000 +0000
++++ examples/liv/scandir.ml
+@@ -31,7 +31,7 @@ let scan_dir f fn =
+         | e -> prerr_endline ("readdir: " ^ Printexc.to_string e)
+       end;
+       closedir dh;
+-      let files = Sort.list (>) !files in
++      let files = List.sort (fun x y -> -compare x y) !files in
+       let subdirs = ref [] in
+       let treat fn' =
+         if not (fn' = ".." || fn' = ".") then begin
Index: pkgsrc/graphics/camlimages/patches/patch-examples_tiffps_tiffps.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-examples_tiffps_tiffps.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-examples_tiffps_tiffps.ml  Sun Dec 26 05:28:23 2021
@@ -0,0 +1,57 @@
+$NetBSD: patch-examples_tiffps_tiffps.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+Silence nuisance warning about lowercase.
+
+--- examples/tiffps/tiffps.ml~ 2011-06-22 18:04:32.000000000 +0000
++++ examples/tiffps/tiffps.ml
+@@ -51,7 +51,7 @@ let parse_length s = (* return in pt *)
+     let digit, unit =
+       if l > 2 then String.sub s 0 2, String.sub s (l-2) 2 else "", "" in
+     try
+-      List.assoc (String.lowercase unit) units *. float_of_string digit
++      List.assoc (String.lowercase_ascii unit) units *. float_of_string digit
+     with
+     | Not_found -> (* think it is in "pt" *) float_of_string s in
+   prerr_endline (Printf.sprintf "%s -> %fpt" s v);
+@@ -59,7 +59,7 @@ let parse_length s = (* return in pt *)
+ 
+ (* Scanlined loader *)
+ type scanlined_loader = {
+-    read_next_line: (string -> unit);
++    read_next_line: (Bytes.t -> unit);
+     close: (unit -> unit)
+   };;
+ 
+@@ -396,7 +396,7 @@ let main () =
+       p "{ currentfile scanline readhexstring pop } false 3";
+       p "colorimage";
+ 
+-      let buf = String.create (imgw * 3) in
++      let buf = Bytes.create (imgw * 3) in
+       for y = 0 to y1 - 1 do th.read_next_line buf done;
+       let prevperdec = ref (-1) in
+       for y = y1 to y1 + h - 1 do
+@@ -411,7 +411,7 @@ let main () =
+             function x ->
+               let adrs = x * 3 in
+               for i = 0 to 2 do
+-                print_string (sprintf "%02x" (Char.code buf.[adrs+i]))
++                print_string (sprintf "%02x" (Char.code (Bytes.get buf (adrs+i))))
+               done
+           else
+             let mono r g b =
+@@ -419,9 +419,9 @@ let main () =
+             function x ->
+               let adrs = x * 3 in
+               let m =
+-                mono (Char.code buf.[adrs])
+-                     (Char.code buf.[adrs + 1])
+-                     (Char.code buf.[adrs + 2]) in
++                mono (Char.code (Bytes.get buf (adrs)))
++                     (Char.code (Bytes.get buf (adrs + 1)))
++                     (Char.code (Bytes.get buf (adrs + 2))) in
+               for i = 0 to 2 do print_string (sprintf "%02x" m) done in
+         if not conf.mirror
+         then for x = x1 to x1 + w - 1 do print_pixel x done
Index: pkgsrc/graphics/camlimages/patches/patch-src_bitmap.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_bitmap.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_bitmap.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,268 @@
+$NetBSD: patch-src_bitmap.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+Sort.list is so old it's not even in the deprecations section of the
+manual any more. Use List.sort.
+
+--- src/bitmap.ml.orig 2011-06-22 18:04:32.000000000 +0000
++++ src/bitmap.ml
+@@ -20,7 +20,7 @@ let maximum_block_size = ref (!maximum_l
+ (* see Temp to set temp file directory *)
+ 
+ type block_data =
+-   | InMemory of string
++   | InMemory of Bytes.t
+    | Swapped
+    | Destroyed;;
+ 
+@@ -35,9 +35,9 @@ type block = {
+ 
+ let swappable_blocks = ref [];;
+ 
+-(* wrapped String.create *)
+-let string_create s =
+-  try String.create s with Invalid_argument _ -> raise Out_of_memory;;
++(* wrapped Bytes.create *)
++let bytes_create s =
++  try Bytes.create s with Invalid_argument _ -> raise Out_of_memory;;
+ 
+ module Block = struct
+   type t = {
+@@ -67,7 +67,7 @@ module Make(B:Bitdepth) = struct
+     blocks_x : int;
+     blocks_y : int;
+     data : block array array;
+-    access : int -> int -> (string * int);
++    access : int -> int -> (Bytes.t * int);
+     };;
+ 
+   (****************************************************************************)
+@@ -92,20 +92,20 @@ module Make(B:Bitdepth) = struct
+            if blk == blk' then st else blk' :: st)
+         !swappable_blocks [];;
+ 
+-  let fill_string buf init =
+-    (* fill string with init quickly (hopefully) *)
+-    let fulllength = String.length buf in
++  let fill_bytes (buf: Bytes.t) (init: string) =
++    (* fill a Bytes with init quickly (hopefully) *)
++    let fulllength = Bytes.length buf in
+     let halflength = fulllength / 2 in
+     let rec sub = function
+       | 0 ->
+         let len = String.length init in
+-        String.unsafe_blit init 0 buf 0 len;
++        Bytes.unsafe_blit_string init 0 buf 0 len;
+         sub len
+       | x when x <= halflength ->
+-        String.unsafe_blit buf 0 buf x x;
++        Bytes.unsafe_blit buf 0 buf x x;
+         sub (x * 2)
+       | x (* when x > halflength *) ->
+-        String.unsafe_blit buf 0 buf x (fulllength - x) in
++        Bytes.unsafe_blit buf 0 buf x (fulllength - x) in
+     sub 0;;
+ 
+   let check_init init =
+@@ -115,7 +115,7 @@ module Make(B:Bitdepth) = struct
+         then failwith "bitmap fill value is incorrect"
+     | None -> ();;
+ 
+-  let memory width height init =
++  let memory width height (init: string option) =
+     (* try to have it whole in memory *)
+ 
+     check_init init;
+@@ -137,11 +137,11 @@ module Make(B:Bitdepth) = struct
+       in
+       (* CR jfuruse: check overflow *)
+       let size = width * height * bytes_per_pixel in
+-      string_create size, size, height)
++      bytes_create size, size, height)
+     in
+     let bufs = Array.map (fun (buf, _, _) -> buf) buf_size_heights in
+     begin match init with
+-    | Some v -> Array.iter (fun s -> fill_string s v) bufs;
++    | Some v -> Array.iter (fun s -> fill_bytes s v) bufs;
+     | None -> ()
+     end;
+     { width = width;
+@@ -186,7 +186,7 @@ module Make(B:Bitdepth) = struct
+ 
+   let swap_out_eldest words =
+     let sorted =
+-      Sort.list (fun b1 b2 -> b1.last_used < b2.last_used) !swappable_blocks in
++      List.sort (fun b1 b2 -> compare b1.last_used b2.last_used) !swappable_blocks in
+     let rec swapper sorted i =
+      match sorted with
+       | [] -> ()
+@@ -213,7 +213,7 @@ module Make(B:Bitdepth) = struct
+           debugs ("swap in "^fname);
+           require size;
+           let ic = open_in_bin fname in
+-          let s = string_create size in
++          let s = bytes_create size in
+           really_input ic s 0 size;
+           close_in ic;
+           blk.block_data <- InMemory s;
+@@ -231,9 +231,9 @@ module Make(B:Bitdepth) = struct
+     (* CR jfuruse: check overflow *)
+     let size = bytes_per_pixel * width * height in
+     require size;
+-    let s = string_create size in
++    let s = bytes_create size in
+     begin match init with
+-    | Some v -> fill_string s v
++    | Some v -> fill_bytes s v
+     | None -> ()
+     end;
+     let blk =
+@@ -271,13 +271,13 @@ module Make(B:Bitdepth) = struct
+               height / p + (if height mod p <> 0 then 1 else 0) in
+         try
+         (* CR jfuruse: check overflow *)
+-          p, string_create
++          p, bytes_create
+                (block_size_width * block_size_height * bytes_per_pixel)
+         with
+         | Out_of_memory -> alloc_test_block (p + 1) in
+       let blocks, test_block = alloc_test_block (get_block_size 1) in
+       (* use the block so that it is not GCed too early *)
+-      test_block.[0] <- '0';
++      Bytes.set test_block 0 '0';
+ 
+       (* Create bitmap *)
+       let blocks_x = blocks
+@@ -336,6 +336,7 @@ module Make(B:Bitdepth) = struct
+     end;;
+ 
+   let create_with width height buf =
++    let bufcopy = Bytes.of_string buf in
+     { width = width;
+       height = height;
+       block_size_width = width;
+@@ -345,13 +346,13 @@ module Make(B:Bitdepth) = struct
+       data =
+         [| [| { block_width = width;
+                 block_height = height;
+-                block_data = InMemory buf;
++                block_data = InMemory bufcopy;
+               (* CR jfuruse: check overflow *)
+                 block_size = width * height * bytes_per_pixel;
+                 last_used = 0.0;
+                 swap = None;
+                } |] |];
+-      access = (fun x y -> buf, (y * width + x) * bytes_per_pixel);
++      access = (fun x y -> bufcopy, (y * width + x) * bytes_per_pixel);
+     };;
+ 
+   let create_with_scanlines width height scanlines =
+@@ -373,6 +374,7 @@ module Make(B:Bitdepth) = struct
+       assert false
+       end
+     done;
++    let scanlines_copy = Array.map Bytes.of_string scanlines in
+     { width = width;
+       height = height;
+       block_size_width = width;
+@@ -383,11 +385,11 @@ module Make(B:Bitdepth) = struct
+       [| Array.mapi (fun y scanline ->
+         { block_width = width;
+             block_height = 1;
+-            block_data = InMemory scanlines.(y);
++            block_data = InMemory scanlines_copy.(y);
+             block_size = block_size;
+             last_used = 0.0;
+             swap = None }) scanlines |];
+-      access = (fun x y -> scanlines.(y), x * bytes_per_pixel);
++      access = (fun x y -> scanlines_copy.(y), x * bytes_per_pixel);
+     };;
+ 
+   (****************************************************************************)
+@@ -410,13 +412,14 @@ module Make(B:Bitdepth) = struct
+       let src = swap_in blk in
+       let size = w * bytes_per_pixel in
+       let adrs = (blk.block_width * y' + x) * bytes_per_pixel in
+-      let str = string_create size in
+-      String.unsafe_blit src adrs str 0 size;
+-      str
++      let str = bytes_create size in
++      Bytes.unsafe_blit src adrs str 0 size;
++      (* safe: just created str and copied to it *)
++      Bytes.unsafe_to_string str
+     | _, _ ->
+       let bly = y / t.block_size_height in
+       let y' = y mod t.block_size_height in
+-      let str = string_create (w * bytes_per_pixel) in
++      let str = bytes_create (w * bytes_per_pixel) in
+       let blx_start = x / t.block_size_width in
+       let blx_last = (x + w - 1) / t.block_size_width in
+       for blx = blx_start to blx_last do
+@@ -433,9 +436,10 @@ module Make(B:Bitdepth) = struct
+         let offset =
+           if blx = blx_start then 0
+           else (t.block_size_width * blx - x) * bytes_per_pixel in
+-        String.unsafe_blit src adrs str offset size
++        Bytes.unsafe_blit src adrs str offset size
+       done;
+-      str;;
++      (* safe: just created str and copied to it *)
++      Bytes.unsafe_to_string str;;
+ 
+   let set_strip t x y w str =
+     (* No region checks for performance. You should wrap this to make safe
+@@ -505,28 +509,29 @@ module Make(B:Bitdepth) = struct
+ 
+   (* dump : of course this does not work for large images *)
+ 
+-  let dump t =
++  (* always produces a fresh bytes, not a pointer into the image *)
++  let dumpbytes t =
+     (* CR jfuruse: check overflow *)
+     let size = bytes_per_pixel * t.width * t.height in
+     match t.blocks_x, t.blocks_y with
+-    | 1, 1 -> swap_in t.data.(0).(0)
++    | 1, 1 -> Bytes.copy (swap_in t.data.(0).(0))
+     | 1, h ->
+-      let s = string_create size in
++      let s = bytes_create size in
+       let scanline_size = bytes_per_pixel * t.width in
+       for y = 0 to h - 1 do
+         let str = swap_in t.data.(0).(y) in
+-        String.unsafe_blit str 0 s (scanline_size * y) scanline_size
++        Bytes.unsafe_blit str 0 s (scanline_size * y) scanline_size
+       done;
+       s
+     | w, h ->
+-      let s = string_create size in
++      let s = bytes_create size in
+       for x = 0 to w - 1 do
+         for y = 0 to h - 1 do
+           let blk = t.data.(x).(y) in
+           let str = swap_in blk in
+           let scanline_size = bytes_per_pixel * blk.block_width in
+           for i = 0 to blk.block_height - 1 do
+-            String.unsafe_blit str (scanline_size * i)
++            Bytes.unsafe_blit str (scanline_size * i)
+               s (((y * t.block_size_height + i) * t.width +
+                     x * t.block_size_width) * bytes_per_pixel)
+               scanline_size
+@@ -535,6 +540,9 @@ module Make(B:Bitdepth) = struct
+       done;
+       s;;
+ 
++  (* safe: dumpbytes always returns a fresh bytes *)
++  let dump t = Bytes.unsafe_to_string (dumpbytes t);;
++
+   (* sub-bitmap *)
+   let sub t x y w h =
+     Region.check t.width t.height x y;
+@@ -575,5 +583,6 @@ module Make(B:Bitdepth) = struct
+       height = h;
+       x = at_x;
+       y = at_y;
+-      dump = swap_in blk }
++      (* copy the data for return *)
++      dump = Bytes.to_string (swap_in blk) }
+ end;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_bitmap.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_bitmap.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_bitmap.mli     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,26 @@
+$NetBSD: patch-src_bitmap.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/bitmap.mli.orig        2011-06-22 18:04:32.000000000 +0000
++++ src/bitmap.mli
+@@ -79,7 +79,7 @@ module Make(B:Bitdepth) : sig
+   val destroy : t -> unit
+     (* Destroy bitmaps *)
+ 
+-  val access : t -> int -> int -> string * int
++  val access : t -> int -> int -> Bytes.t * int
+ 
+   val get_strip : t -> int -> int -> int -> string
+   val set_strip : t -> int -> int -> int -> string -> unit
+@@ -100,8 +100,9 @@ module Make(B:Bitdepth) : sig
+     *)
+ 
+   (* only for one row *)      
+-  val get_scanline_ptr : t -> (int -> (string * int) * int) option
++  val get_scanline_ptr : t -> (int -> (Bytes.t * int) * int) option
+ 
++  val dumpbytes : t -> Bytes.t
+   val dump : t -> string
+     (* Create a string representation of a bitmap. It may easily raise
+        an exception Out_of_memory for large images. *)
Index: pkgsrc/graphics/camlimages/patches/patch-src_bmp.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_bmp.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_bmp.ml Sun Dec 26 05:28:23 2021
@@ -0,0 +1,237 @@
+$NetBSD: patch-src_bmp.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/bmp.ml.orig    2011-06-22 18:04:32.000000000 +0000
++++ src/bmp.ml
+@@ -32,7 +32,7 @@ type bmp = {
+    bmpFileHeader : bitmapfileheader;           (* Bytes <0  14< *)
+    bmpInfoHeader : bitmapinfoheader;           (* Bytes <14 54< *)
+    bmpRgbQuad : rgb array;                     (* Bytes <54 ... *)
+-   bmpBytes : string;                          (* Bytes <bfOffBits ... *)
++   bmpBytes : Bytes.t;                         (* Bytes <bfOffBits ... *)
+ }
+ 
+ and bitmapfileheader = {
+@@ -221,7 +221,7 @@ let load_colors bfh _bih ic =
+ 
+ (* Loads image data when image has 8 bit depth *)
+ let load_image8data bih ic =
+- let bitmap = String.create (bih.biWidth * bih.biHeight) in
++ let bitmap = Bytes.create (bih.biWidth * bih.biHeight) in
+  match bih.biCompression with
+  | BI_RGB ->
+      (* No compression : lines are stored in reverse order *)
+@@ -232,7 +232,7 @@ let load_image8data bih ic =
+        let bitmapindex = ref (i * bih.biWidth) in
+        for j = 0 to pad - 1 do
+          let c = Char.chr (read_byte ic) in
+-         if j < bih.biWidth then bitmap.[!bitmapindex] <- c;
++         if j < bih.biWidth then Bytes.set bitmap !bitmapindex c;
+          incr bitmapindex
+          done
+        done;
+@@ -273,7 +273,7 @@ let load_image8data bih ic =
+                   each of which contains the color index of a single pixel. *)
+                for i = 0 to c - 1 do
+                  let c1 = read_byte ic in
+-                 bitmap.[!bitmapindex] <- Char.chr c1;
++                 Bytes.set bitmap !bitmapindex (Char.chr c1);
+                  incr x;
+                  incr bitmapindex
+                done;
+@@ -284,7 +284,7 @@ let load_image8data bih ic =
+            (* Encoded mode *)
+            let c1 = read_byte ic in
+            for i = 0 to c - 1 do
+-             bitmap.[!bitmapindex] <- Char.chr c1;
++             Bytes.set bitmap !bitmapindex (Char.chr c1);
+              incr x;
+              incr bitmapindex
+            done
+@@ -295,7 +295,7 @@ let load_image8data bih ic =
+ ;;
+ 
+ let load_image1data bih ic =
+- let bitmap = String.create (bih.biWidth * bih.biHeight) in
++ let bitmap = Bytes.create (bih.biWidth * bih.biHeight) in
+  let c = ref 0 in
+  (* each scan line 'w', is padded to be a multiple of 32 *)
+  let pad = ((bih.biWidth + 31) / 32) * 32 in
+@@ -311,7 +311,7 @@ let load_image1data bih ic =
+       end;
+      if j < bih.biWidth then
+       begin
+-       bitmap.[!bitmapindex] <- if !c land 0x80 <> 0 then '\001' else '\000';
++       Bytes.set bitmap !bitmapindex (if !c land 0x80 <> 0 then '\001' else '\000');
+        incr bitmapindex;
+        c := !c lsl 1;
+       end;
+@@ -322,7 +322,7 @@ let load_image1data bih ic =
+ ;;
+ 
+ let load_image4data bih ic =
+- let bitmap = String.create (bih.biWidth * bih.biHeight) in
++ let bitmap = Bytes.create (bih.biWidth * bih.biHeight) in
+  match bih.biCompression with
+  | BI_RGB ->
+     (* 'w' is padded to be a multiple of 8 pixels (32 bits) *)
+@@ -341,7 +341,7 @@ let load_image4data bih ic =
+           end;
+         if j < bih.biWidth then
+           begin
+-          bitmap.[!bitmapindex] <- Char.chr ((!c land 0xf0) lsr 4);
++          Bytes.set bitmap !bitmapindex (Char.chr ((!c land 0xf0) lsr 4));
+           incr bitmapindex;
+           c := !c lsl 4
+           end;
+@@ -380,7 +380,7 @@ let load_image4data bih ic =
+               for i = 0 to c - 1 do
+                 if i land 1 = 0 then c1 := read_byte ic;
+                 let c = if i land 1 <> 0 then !c1 else !c1 lsr 4 in
+-                bitmap.[!bitmapindex] <- Char.chr (c land 0x0F);
++                Bytes.set bitmap !bitmapindex (Char.chr (c land 0x0F));
+                 incr x;
+                 incr bitmapindex
+               done;
+@@ -395,7 +395,7 @@ let load_image4data bih ic =
+           and col2 = (c1 lsr 4) land 0x0F in
+           for i = 0 to c - 1 do
+             let c = if i land 1 <> 0 then col1 else col2 in
+-            bitmap.[!bitmapindex] <- Char.chr c;
++            Bytes.set bitmap !bitmapindex (Char.chr c);
+             incr x;
+             incr bitmapindex
+           done
+@@ -407,15 +407,15 @@ let load_image4data bih ic =
+ 
+ let load_image24data bih ic =
+   (* Bitmap is a string of RGB bytes *)
+-  let bitmap = String.create ((bih.biWidth * bih.biHeight) * 3) in
++  let bitmap = Bytes.create ((bih.biWidth * bih.biHeight) * 3) in
+   let pad = (4 - ((bih.biWidth * 3) mod 4)) land 0x03 in
+   let pp = ref 0 in
+   for i = bih.biHeight - 1 downto 0 do
+     pp := (i * bih.biWidth * 3);
+     for j = 0 to bih.biWidth - 1 do
+-      bitmap.[!pp + 2] <- Char.chr (read_byte ic);   (* Blue *)
+-      bitmap.[!pp + 1] <- Char.chr (read_byte ic);   (* Green *)
+-      bitmap.[!pp] <- Char.chr (read_byte ic);     (* Red *)
++      Bytes.set bitmap (!pp + 2) (Char.chr (read_byte ic));   (* Blue *)
++      Bytes.set bitmap (!pp + 1) (Char.chr (read_byte ic));   (* Green *)
++      Bytes.set bitmap (!pp    ) (Char.chr (read_byte ic));   (* Red *)
+       pp := !pp + 3
+     done;
+     for j = 0 to pad - 1 do skip_byte ic done;
+@@ -478,13 +478,15 @@ let image_of_bmp = function
+    bmpInfoHeader = bih;
+    bmpRgbQuad = colormap;
+    bmpBytes = bitmap; } ->
++   (* safe: we pass it only to create_with, which copies it *)
++   let bitmap' = Bytes.unsafe_to_string bitmap in
+    match bih.biBitCount with
+    | ColorM ->
+-       Rgb24 (Rgb24.create_with bih.biWidth bih.biHeight [] bitmap)
++       Rgb24 (Rgb24.create_with bih.biWidth bih.biHeight [] bitmap')
+    | _ ->
+        Index8
+          (Index8.create_with bih.biWidth bih.biHeight []
+-            { map = colormap; max = 256; } (-1) bitmap)
++            { map = colormap; max = 256; } (-1) bitmap')
+ ;;
+ 
+ let load fname _opts = image_of_bmp (read_bmp_file fname);;
+@@ -661,7 +663,7 @@ let write_image1data bmp oc =
+    if count = 8 then begin
+      write_byte oc accu;
+      if x <= lim then write_line x 0 0 end else
+-   let cur = bitmap.[x] in
++   let cur = Bytes.get bitmap x in
+    let chunk = Char.code cur lsl (7 - count) in
+    let new_accu = chunk + accu in
+    if x = lim then write_byte oc new_accu
+@@ -693,9 +695,9 @@ let write_image24data bmp oc =
+   let start = i * width * 3 in
+   let lim = (i + 1) * width * 3 - 1 in
+   let rec write_line x =
+-   write_byte oc (Char.code bitmap.[x + 2]);   (* Blue *)
+-   write_byte oc (Char.code bitmap.[x + 1]);   (* Green *)
+-   write_byte oc (Char.code bitmap.[x]);       (* Red *)
++   write_byte oc (Char.code (Bytes.get bitmap (x + 2)));   (* Blue *)
++   write_byte oc (Char.code (Bytes.get bitmap (x + 1)));   (* Green *)
++   write_byte oc (Char.code (Bytes.get bitmap (x)));       (* Red *)
+    let new_x = x + 3 in
+    if new_x < lim then write_line new_x in
+ 
+@@ -730,7 +732,7 @@ let write_image4data bmp oc =
+       if count = 2 then begin
+        write_byte oc accu;
+        if x <= lim then write_line x 0 0 end else
+-      let cur = bitmap.[x] in
++      let cur = Bytes.get bitmap x in
+       let chunk = Char.code cur lsl (4 - count) in
+       let new_accu = chunk + accu in
+       if x = lim then write_byte oc new_accu
+@@ -755,7 +757,7 @@ let write_image4data bmp oc =
+      let start = i * width in
+      let lim = (i + 1) * width - 1 in
+      let rec write_line x count pred =
+-      let cur = bitmap.[x] in
++      let cur = Bytes.get bitmap x in
+       if cur = pred then
+        if x = lim then write_rle4 oc (count + 1) pred
+        else write_line (x + 1) (count + 1) pred
+@@ -764,7 +766,7 @@ let write_image4data bmp oc =
+        if x = lim then write_rle4 oc 1 cur
+        else write_line (x + 1) 1 cur
+       end in
+-     write_line start 0 bitmap.[start];
++     write_line start 0 (Bytes.get bitmap start);
+      write_end_of_scan_line oc;
+      (* No padding in this mode *)
+     done;
+@@ -794,7 +796,7 @@ let write_image8data bmp oc =
+      let start = i * width in
+      let lim = (i + 1) * width - 1 in
+      let rec write_line x =
+-      let cur = bitmap.[x] in
++      let cur = Bytes.get bitmap x in
+       write_byte oc (Char.code cur);
+       if x < lim then write_line (x + 1) in
+ 
+@@ -817,7 +819,7 @@ let write_image8data bmp oc =
+      let start = i * width in
+      let lim = (i + 1) * width - 1 in
+      let rec write_line x count pred =
+-      let cur = bitmap.[x] in
++      let cur = Bytes.get bitmap x in
+       if cur = pred then
+        if x = lim then write_rle oc (count + 1) pred
+        else write_line (x + 1) (count + 1) pred
+@@ -826,7 +828,7 @@ let write_image8data bmp oc =
+        if x = lim then write_rle oc 1 cur
+        else write_line (x + 1) 1 cur
+       end in
+-     write_line start 0 bitmap.[start];
++     write_line start 0 (Bytes.get bitmap start);
+      write_end_of_scan_line oc;
+      (* No padding in this mode *)
+     done;
+@@ -851,7 +853,7 @@ let bmp_of_image img =
+   | Rgb24 bitmap ->
+     let biW = bitmap.Rgb24.width
+     and biH = bitmap.Rgb24.height
+-    and data = Rgb24.dump bitmap in
++    and data = Rgb24.dumpbytes bitmap in
+     let bfh = {
+       (* WORD *) bfType = 19778 (* BM *);
+       (* DWORD *) bfSize = -1 (* Unknown to be updated *);
+@@ -892,7 +894,7 @@ let bmp_of_image img =
+     let colormap = bitmap.Index8.colormap.map
+     and biW = bitmap.Index8.width
+     and biH = bitmap.Index8.height
+-    and data = Index8.dump bitmap in
++    and data = Index8.dumpbytes bitmap in
+     let bfh = {
+       (* WORD *) bfType = 19778 (* BM *);
+       (* DWORD *) bfSize = -1 (* Unknown to be updated *);
Index: pkgsrc/graphics/camlimages/patches/patch-src_bmp.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_bmp.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_bmp.mli        Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_bmp.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/bmp.mli~       2011-06-22 18:04:32.000000000 +0000
++++ src/bmp.mli
+@@ -39,7 +39,7 @@ type bmp = {
+    bmpFileHeader : bitmapfileheader;           (** Bytes <0  14< *)
+    bmpInfoHeader : bitmapinfoheader;           (** Bytes <14 54< *)
+    bmpRgbQuad : Images.rgb array;              (** Bytes <54 ... *)
+-   bmpBytes : string;                          (** Bytes <bfOffBits ... *)
++   bmpBytes : Bytes.t;                         (** Bytes <bfOffBits ... *)
+ }
+ 
+ and bitmapfileheader = {
Index: pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,33 @@
+$NetBSD: patch-src_cmyk32.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/cmyk32.ml.orig 2011-06-22 18:04:32.000000000 +0000
++++ src/cmyk32.ml
+@@ -21,17 +21,17 @@ module E = struct
+   type t = Color.cmyk
+   let bytes_per_pixel = 4
+   let get str pos =
+-    { c = int_of_char str.[pos    ];
+-      m = int_of_char str.[pos + 1];
+-      y = int_of_char str.[pos + 2];
+-      k = int_of_char str.[pos + 3]; }
++    { c = int_of_char (Bytes.get str (pos    ));
++      m = int_of_char (Bytes.get str (pos + 1));
++      y = int_of_char (Bytes.get str (pos + 2));
++      k = int_of_char (Bytes.get str (pos + 3)); }
+   let set str pos t =
+-    str.[pos    ] <- char_of_int t.c;
+-    str.[pos + 1] <- char_of_int t.m;
+-    str.[pos + 2] <- char_of_int t.y;
+-    str.[pos + 3] <- char_of_int t.k
++    Bytes.set str (pos    ) (char_of_int t.c);
++    Bytes.set str (pos + 1) (char_of_int t.m);
++    Bytes.set str (pos + 2) (char_of_int t.y);
++    Bytes.set str (pos + 3) (char_of_int t.k)
+   let make t =
+-    let str = String.create bytes_per_pixel in
++    let str = Bytes.create bytes_per_pixel in
+     set str 0 t;
+     str
+ end;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_cmyk32.mli     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_cmyk32.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/cmyk32.mli~    2011-06-22 18:04:32.000000000 +0000
++++ src/cmyk32.mli
+@@ -32,7 +32,7 @@ type t = {
+ (* Please read the comments of IMAGE in genimage.mli *)
+ 
+ val dump : t -> string;;
+-val unsafe_access : t -> int -> int -> string * int;;
++val unsafe_access : t -> int -> int -> Bytes.t * int;;
+ val get_strip : t -> int -> int -> int -> string;;
+ val set_strip : t -> int -> int -> int -> string -> unit;;
+ val get_scanline : t -> int -> string;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_genimage.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_genimage.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_genimage.ml    Sun Dec 26 05:28:23 2021
@@ -0,0 +1,35 @@
+$NetBSD: patch-src_genimage.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/genimage.ml.orig       2011-06-22 18:04:32.000000000 +0000
++++ src/genimage.ml
+@@ -33,6 +33,7 @@ module MakeRawImage(E:ENCODE) = struct
+ 
+   let width t = t.width
+   let height t = t.height
++  let dumpbytes t = Bitmap.dumpbytes t.bitmap
+   let dump t = Bitmap.dump t.bitmap
+ 
+   let create_with width height init_buffer =
+@@ -57,9 +58,11 @@ module MakeRawImage(E:ENCODE) = struct
+   ;;
+ 
+   let make width height init =
++    (* safe: make returns a fresh bytes AND create copies it *)
++    let init' = Bytes.unsafe_to_string (E.make init) in
+     { width= width;
+       height= height;
+-      bitmap= Bitmap.create width height (Some (E.make init));
++      bitmap= Bitmap.create width height (Some init');
+     }
+   ;;
+ 
+@@ -126,6 +129,7 @@ module Make(RI:RAWIMAGE)(CON:CONTAINER w
+   type elt = RI.elt
+ 
+   let dump t = RI.dump (CON.rawimage t)
++  let dumpbytes t = RI.dumpbytes (CON.rawimage t)
+ 
+   let create width height =
+     CON.create_default width height (RI.create width height)
Index: pkgsrc/graphics/camlimages/patches/patch-src_gif.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_gif.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_gif.ml Sun Dec 26 05:28:23 2021
@@ -0,0 +1,99 @@
+$NetBSD: patch-src_gif.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/gif.ml.orig    2011-06-22 18:04:32.000000000 +0000
++++ src/gif.ml
+@@ -58,7 +58,7 @@ external dGifGetRecordType : in_channel 
+     = "dGifGetRecordType";;
+ external dGifGetImageDesc : in_channel -> gif_desc
+     = "dGifGetImageDesc";;
+-external dGifGetLine : in_channel -> string
++external dGifGetLine : in_channel -> Bytes.t
+     = "dGifGetLine";;
+ external dGifGetExtension : in_channel -> int * string list (* reversed!!! *)
+     = "dGifGetExtension";;
+@@ -200,7 +200,8 @@ let load filename opts =
+            let rec loop src dest dest_step =
+              if dest >= desc.desc_height then src else begin
+                let line = dGifGetLine ic in
+-               Index8.set_scanline img dest line;
++               (* safe: set_scanline copies it *)
++               Index8.set_scanline img dest (Bytes.unsafe_to_string line);
+                incr lines;
+                begin match prog with
+                | Some p -> p (float !lines /. float desc.desc_height)
+@@ -216,7 +217,8 @@ let load filename opts =
+          let normal_reader () =
+            for y = 0 to desc.desc_height - 1 do
+              let line = dGifGetLine ic in
+-             Index8.set_scanline img y line;
++             (* safe: set_scanline copies it *)
++             Index8.set_scanline img y (Bytes.unsafe_to_string line);
+              begin match prog with
+              | Some p -> p (float (y + 1) /. float desc.desc_height)
+              | None -> ()
+@@ -345,12 +347,12 @@ let save filename opts sequence =
+     (* write loops *)
+     let loop_written = ref false in
+     if sequence.loops <> 0 then begin
+-      let str = String.create 3 in
+-      str.[0] <- '\001';
+-      str.[1] <- char_of_int (sequence.loops mod 256);
+-      str.[2] <- char_of_int (sequence.loops / 256);
++      let str = Bytes.create 3 in
++      Bytes.set str 0 '\001';
++      Bytes.set str 1 (char_of_int (sequence.loops mod 256));
++      Bytes.set str 2 (char_of_int (sequence.loops / 256));
+       eGifPutExtension oc
+-        (gif_make_extension (GifApplication ["NETSCAPE2.0"; str]));
++        (gif_make_extension (GifApplication ["NETSCAPE2.0"; Bytes.to_string str]));
+       loop_written := true
+     end;
+ 
+@@ -382,18 +384,18 @@ let save filename opts sequence =
+          frame.frame_bitmap.transparent <> -1 then begin
+         let str =
+           match !graphics_ext with
+-          | Some str -> str
+-          | None -> String.make 4 '\000' in
++          | Some str -> Bytes.of_string str
++          | None -> Bytes.make 4 '\000' in
+         if frame.frame_bitmap.transparent <> -1 then begin
+-          str.[0] <- char_of_int (int_of_char str.[0] lor 0x01);
+-          str.[3] <- char_of_int frame.frame_bitmap.transparent
++          Bytes.set str 0 (char_of_int (int_of_char (Bytes.get str 0) lor 0x01));
++          Bytes.set str 3 (char_of_int frame.frame_bitmap.transparent)
+         end else begin
+-          str.[0] <- char_of_int (int_of_char str.[0] land 0xfe);
+-          str.[3] <- '\000'
++          Bytes.set str 0 (char_of_int (int_of_char (Bytes.get str 0) land 0xfe));
++          Bytes.set str 3 '\000'
+         end;
+-        str.[1] <- char_of_int (frame.frame_delay mod 256);
+-        str.[2] <- char_of_int (frame.frame_delay / 256);
+-        eGifPutExtension oc (gif_make_extension (GifGraphics [str]))
++        Bytes.set str 1 (char_of_int (frame.frame_delay mod 256));
++        Bytes.set str 2 (char_of_int (frame.frame_delay / 256));
++        eGifPutExtension oc (gif_make_extension (GifGraphics [Bytes.to_string str]))
+       end;
+ 
+       let bmp = frame.frame_bitmap in
+@@ -456,13 +458,13 @@ let check_header filename =
+   let len = 10 in
+   let ic = open_in_bin filename in
+   try
+-    let str = String.create len in
++    let str = Bytes.create len in
+     really_input ic str 0 len;
+     close_in ic;
+-    match String.sub str 0 6 with
++    match Bytes.sub_string str 0 6 with
+     | "GIF87a" | "GIF89a" -> {
+-         header_width = int_of_char str.[6] + int_of_char str.[7] * 256;
+-         header_height = int_of_char str.[8] + int_of_char str.[9] * 256;
++         header_width = int_of_char (Bytes.get str 6) + int_of_char (Bytes.get str 7) * 256;
++         header_height = int_of_char (Bytes.get str 8) + int_of_char (Bytes.get str 9) * 256;
+          header_infos = [];
+        }
+     | _ -> raise Wrong_file_type
Index: pkgsrc/graphics/camlimages/patches/patch-src_gif.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_gif.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_gif.mli        Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_gif.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/gif.mli.orig   2011-06-22 18:04:32.000000000 +0000
++++ src/gif.mli
+@@ -85,7 +85,7 @@ val dGifOpenFileName : string -> screen_
+ val dGifCloseFile : in_channel -> unit;;
+ val dGifGetRecordType : in_channel -> record_type;;
+ val dGifGetImageDesc : in_channel -> gif_desc;;
+-val dGifGetLine : in_channel -> string;;
++val dGifGetLine : in_channel -> Bytes.t;;
+ val dGifGetExtension : in_channel -> int * string list;;
+ 
+ val eGifOpenFileName : string -> out_channel;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_image__intf.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_image__intf.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_image__intf.mli        Sun Dec 26 05:28:23 2021
@@ -0,0 +1,53 @@
+$NetBSD: patch-src_image__intf.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/image_intf.mli.orig    2011-06-22 18:04:32.000000000 +0000
++++ src/image_intf.mli
+@@ -19,9 +19,9 @@ module type ENCODE =
+   sig
+     type t
+     val bytes_per_pixel : int
+-    val get : string -> int -> t
+-    val set : string -> int -> t -> unit
+-    val make : t -> string
++    val get : Bytes.t -> int -> t
++    val set : Bytes.t -> int -> t -> unit
++    val make : t -> Bytes.t
+   end;;
+ 
+ (** Low level image module type *)
+@@ -33,15 +33,16 @@ module type RAWIMAGE = sig
+   val width : t -> int
+   val height : t -> int
+   val dump : t -> string
++  val dumpbytes : t -> Bytes.t
+   val create_with : int -> int -> string -> t
+   val create_with_scanlines : int -> int -> string array -> t
+   val create : int -> int -> t
+   val make : int -> int -> elt -> t
+-  val unsafe_access : t -> int -> int -> string * int
++  val unsafe_access : t -> int -> int -> Bytes.t * int
+   val get_strip : t -> int -> int -> int -> string
+   val set_strip : t -> int -> int -> int -> string -> unit
+   val get_scanline : t -> int -> string
+-  val get_scanline_ptr : t -> (int -> (string * int) * int) option
++  val get_scanline_ptr : t -> (int -> (Bytes.t * int) * int) option
+   val set_scanline : t -> int -> string -> unit
+   val unsafe_get : t -> int -> int -> elt
+   val unsafe_set : t -> int -> int -> elt -> unit
+@@ -126,11 +127,12 @@ module type IMAGE = sig
+ 
+   (** functions for internal use *)
+   val dump : t -> string
+-  val unsafe_access : t -> int -> int -> string * int
++  val dumpbytes : t -> Bytes.t
++  val unsafe_access : t -> int -> int -> Bytes.t * int
+   val get_strip : t -> int -> int -> int -> string
+   val set_strip : t -> int -> int -> int -> string -> unit
+   val get_scanline : t -> int -> string
+-  val get_scanline_ptr : t -> (int -> (string * int) * int) option
++  val get_scanline_ptr : t -> (int -> (Bytes.t * int) * int) option
+   val set_scanline : t -> int -> string -> unit
+   val blocks : t -> int * int
+   val dump_block : t -> int -> int -> Bitmap.Block.t
Index: pkgsrc/graphics/camlimages/patches/patch-src_imagegdk.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_imagegdk.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_imagegdk.ml    Sun Dec 26 05:28:23 2021
@@ -0,0 +1,34 @@
+$NetBSD: patch-src_imagegdk.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for OCaml immutable strings.
+
+--- src/imagegdk.ml.orig       2011-06-22 18:04:32.000000000 +0000
++++ src/imagegdk.ml
+@@ -31,7 +31,7 @@ let draw (obj : #GDraw.drawable) ?x ?y ?
+   match tag image, image#blocks with
+   | Rgb24 image, (1,1) ->
+       let string = fst (image#unsafe_access 0 0) in
+-      let buf = Gpointer.region_of_string string in
++      let buf = Gpointer.region_of_bytes string in
+       obj#put_rgb_data ~width: image#width ~height: image#height
+       ?x ?y ?dither ~row_stride:(image#width * 3) buf
+   | _ -> failwith "Gdkrgb.draw"
+@@ -41,7 +41,7 @@ let to_pixbuf image =
+   match tag image, image#blocks with
+   | Rgb24 image, (1,1) ->
+       let string = fst (image#unsafe_access 0 0) in
+-      let buf = Gpointer.region_of_string string in
++      let buf = Gpointer.region_of_bytes string in
+       (* string may be GC'ed here? *)
+       let pixbuf = 
+       GdkPixbuf.from_data ~width: image#width ~height: image#height
+@@ -58,7 +58,8 @@ let to_pixbuf image =
+         let blk = image#dump_block x y in
+         let width = blk.Bitmap.Block.width in
+         let height = blk.Bitmap.Block.height in
+-        let buf = Gpointer.region_of_string blk.Bitmap.Block.dump in
++          (* safe: temporary readonly access *)
++        let buf = Gpointer.region_of_bytes (Bytes.unsafe_of_string blk.Bitmap.Block.dump) in
+         let pixbuf =
+           GdkPixbuf.from_data ~width ~height ~bits: 8
+             ~rowstride:(width * 3) ~has_alpha: false buf 
Index: pkgsrc/graphics/camlimages/patches/patch-src_images.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_images.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_images.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_images.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Silence nuisance warning about lowercase.
+
+--- src/images.ml~     2011-06-22 18:04:32.000000000 +0000
++++ src/images.ml
+@@ -102,7 +102,7 @@ let get_extension s =
+   | _ -> s, "";;
+ 
+ let guess_extension s =
+-  let s = String.lowercase s in
++  let s = String.lowercase_ascii s in
+   match s with
+   | "gif" -> Gif
+   | "bmp" -> Bmp
Index: pkgsrc/graphics/camlimages/patches/patch-src_index16.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_index16.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_index16.ml     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,25 @@
+$NetBSD: patch-src_index16.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/index16.ml.orig        2011-06-22 18:04:32.000000000 +0000
++++ src/index16.ml
+@@ -19,13 +19,13 @@ module E = struct
+   type t = int
+   let bytes_per_pixel = 2
+   let get str pos =
+-    int_of_char str.[pos    ] * 256 +
+-    int_of_char str.[pos + 1]
++    int_of_char (Bytes.get str (pos    )) * 256 +
++    int_of_char (Bytes.get str (pos + 1))
+   let set str pos t =
+-    str.[pos    ] <- char_of_int (t / 256);
+-    str.[pos + 1] <- char_of_int (t mod 256)
++    Bytes.set str (pos    ) (char_of_int (t / 256));
++    Bytes.set str (pos + 1) (char_of_int (t mod 256))
+   let make t =
+-    let str = String.create bytes_per_pixel in
++    let str = Bytes.create bytes_per_pixel in
+     set str 0 t;
+     str
+ end;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_index16.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_index16.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_index16.mli    Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_index16.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/index16.mli~   2011-06-22 18:04:32.000000000 +0000
++++ src/index16.mli
+@@ -40,7 +40,7 @@ val to_rgba32 : ?failsafe: Color.rgba ->
+ (** Please read the comments of IMAGEINDEXED in genimage.mli *)
+ 
+ val dump : t -> string;;
+-val unsafe_access : t -> int -> int -> string * int;;
++val unsafe_access : t -> int -> int -> Bytes.t * int;;
+ val get_strip : t -> int -> int -> int -> string;;
+ val set_strip : t -> int -> int -> int -> string -> unit;;
+ val get_scanline : t -> int -> string;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_index8.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_index8.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_index8.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,29 @@
+$NetBSD: patch-src_index8.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/index8.ml.orig 2011-06-22 18:04:32.000000000 +0000
++++ src/index8.ml
+@@ -19,11 +19,11 @@ module E = struct
+   type t = int
+   let bytes_per_pixel = 1
+   let get str pos =
+-    int_of_char str.[pos]
++    int_of_char (Bytes.get str pos)
+   let set str pos t =
+-    str.[pos] <- char_of_int t
++    Bytes.set str pos (char_of_int t)
+   let make t =
+-    let str = String.create bytes_per_pixel in
++    let str = Bytes.create bytes_per_pixel in
+     set str 0 t;
+     str
+ end;;
+@@ -87,6 +87,7 @@ let rawimage = C.rawimage;;
+ let create = IMAGE.create;;
+ let make = IMAGE.make;;
+ let dump = IMAGE.dump;;
++let dumpbytes = IMAGE.dumpbytes;;
+ let unsafe_access = IMAGE.unsafe_access;;
+ let get_strip = IMAGE.get_strip;;
+ let set_strip = IMAGE.set_strip;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_index8.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_index8.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_index8.mli     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,16 @@
+$NetBSD: patch-src_index8.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/index8.mli~    2011-06-22 18:04:32.000000000 +0000
++++ src/index8.mli
+@@ -40,7 +40,8 @@ val to_rgba32 : ?failsafe: Color.rgba ->
+ (** Please read the comments of IMAGEINDEXED in genimage.mli *)
+ 
+ val dump : t -> string;;
+-val unsafe_access : t -> int -> int -> string * int;;
++val dumpbytes : t -> Bytes.t;;
++val unsafe_access : t -> int -> int -> Bytes.t * int;;
+ val get_strip : t -> int -> int -> int -> string;;
+ val set_strip : t -> int -> int -> int -> string -> unit;;
+ val get_scanline : t -> int -> string;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_jpeg.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_jpeg.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_jpeg.ml        Sun Dec 26 05:28:23 2021
@@ -0,0 +1,162 @@
+$NetBSD: patch-src_jpeg.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+Use "Stdlib" instead of "Pervasives".
+
+--- src/jpeg.ml.orig   2011-06-22 18:04:32.000000000 +0000
++++ src/jpeg.ml
+@@ -17,7 +17,7 @@
+ open Images;;
+ open Rgb24;;
+ 
+-external read : string -> int * int * string
++external read : string -> int * int * Bytes.t
+     = "read_JPEG_file";;
+ external write : string -> string -> int -> int -> int -> unit
+     = "write_JPEG_file";;
+@@ -30,9 +30,9 @@ external set_scale_denom : in_handle -> 
+     = "jpeg_set_scale_denom";;
+ external open_in_start : in_handle -> int * int * in_handle
+     = "open_jpeg_file_for_read_start";;
+-external read_scanline : in_handle -> string -> int -> unit
++external read_scanline : in_handle -> Bytes.t -> int -> unit
+     = "read_jpeg_scanline";;
+-external read_scanlines : in_handle -> string -> int -> int -> unit
++external read_scanlines : in_handle -> Bytes.t -> int -> int -> unit
+     = "read_jpeg_scanlines";;
+ external close_in : in_handle -> unit
+     = "close_jpeg_file_for_read";;
+@@ -95,10 +95,11 @@ let load_aux prog ic w h = 
+       load_scanlines 0
+   | None -> 
+       (* CR jfuruse: check overflow *)
+-      let scanline = String.create (w * 3) in
++      let scanline = Bytes.create (w * 3) in
+       for y = 0 to h - 1 do
+       read_scanline ic scanline 0;
+-      Rgb24.set_scanline img y scanline;
++        (* safe: set_scanline copies it *)
++      Rgb24.set_scanline img y (Bytes.unsafe_to_string scanline);
+       prog y
+       done
+   end;
+@@ -141,16 +142,16 @@ let save_as_cmyk name opts trans image =
+     | None -> 80 in
+   let prog = Images.save_progress opts in
+   let get_cmyk_scanline width scanline =
+-    let buf = String.create (width * 4) in
++    let buf = Bytes.create (width * 4) in
+     for x = 0 to width - 1 do
+       let r = int_of_char scanline.[x * 3 + 0] in
+       let g = int_of_char scanline.[x * 3 + 1] in
+       let b = int_of_char scanline.[x * 3 + 2] in
+       let c, m, y, k = trans {r = r; g = g; b = b} in
+-      buf.[x * 4 + 0] <- char_of_int (255 - c);
+-      buf.[x * 4 + 1] <- char_of_int (255 - m);
+-      buf.[x * 4 + 2] <- char_of_int (255 - y);
+-      buf.[x * 4 + 3] <- char_of_int (255 - k)
++      Bytes.set buf (x * 4 + 0) (char_of_int (255 - c));
++      Bytes.set buf (x * 4 + 1) (char_of_int (255 - m));
++      Bytes.set buf (x * 4 + 2) (char_of_int (255 - y));
++      Bytes.set buf (x * 4 + 3) (char_of_int (255 - k))
+     done;
+     buf in
+   match image with
+@@ -158,7 +159,8 @@ let save_as_cmyk name opts trans image =
+       let oc = open_out_cmyk name bmp.width bmp.height quality in
+       for y = 0 to bmp.height - 1 do
+         let buf = get_cmyk_scanline bmp.width (Rgb24.get_scanline bmp y) in
+-        write_scanline oc buf;
++        (* safe: write_scanline does not keep a reference *)
++        write_scanline oc (Bytes.unsafe_to_string buf);
+         match prog with
+         | Some p -> p (float (y + 1) /. float bmp.height)
+         | None -> ()
+@@ -179,19 +181,20 @@ let save_cmyk_sample name opts =
+     and k = (y mod 16) * 17 in
+     c, m, y, k in
+   let sample_scan y =
+-    let s = String.create (256 * 4) in
++    let s = Bytes.create (256 * 4) in
+     for x = 0 to 255 do
+       let c, m, y, k = sample_point x y in
+-      s.[x * 4 + 0] <- char_of_int c;
+-      s.[x * 4 + 1] <- char_of_int m;
+-      s.[x * 4 + 2] <- char_of_int y;
+-      s.[x * 4 + 3] <- char_of_int k;
++      Bytes.set s (x * 4 + 0) (char_of_int c);
++      Bytes.set s (x * 4 + 1) (char_of_int m);
++      Bytes.set s (x * 4 + 2) (char_of_int y);
++      Bytes.set s (x * 4 + 3) (char_of_int k);
+     done;
+     s in
+   let oc = open_out_cmyk name 256 256 quality in
+   for y = 0 to 256 - 1 do
+     let buf = sample_scan y in
+-    write_scanline oc buf
++    (* safe: write_scanline does not keep a reference *)
++    write_scanline oc (Bytes.unsafe_to_string buf)
+   done;
+   close_out oc;;
+ 
+@@ -207,20 +210,20 @@ let rec find_jpeg_size ic =
+       else ch in
+     jump_to_0xff ();
+     let ch = jump_to_non_0xff () in
+-    let str = String.create 4 in
++    let str = Bytes.create 4 in
+     match ch with
+     | 0xda -> raise Not_found
+     | _ when ch >= 0xc0 && ch <= 0xc3 ->
+       really_input ic str 0 3;
+       really_input ic str 0 4;
+-      int_of_char str.[2] lsl 8 + int_of_char str.[3], (* width *)
+-      int_of_char str.[0] lsl 8 + int_of_char str.[1]  (* height *)
++      int_of_char (Bytes.get str 2) lsl 8 + int_of_char (Bytes.get str 3), (* width *)
++      int_of_char (Bytes.get str 0) lsl 8 + int_of_char (Bytes.get str 1)  (* height *)
+     | _ ->
+       (* skip this block *)
+       let blocklen =
+         really_input ic str 0 2;
+-        int_of_char str.[0] lsl 8 + int_of_char str.[1] in
+-      let s = String.create (blocklen - 2) in
++        int_of_char (Bytes.get str 0) lsl 8 + int_of_char (Bytes.get str 1) in
++      let s = Bytes.create (blocklen - 2) in
+       really_input ic s 0 (blocklen - 2);
+       loop () in
+   try loop () with
+@@ -230,18 +233,18 @@ let check_header filename =
+   let len = 2 in
+   let ic = open_in_bin filename in
+   try
+-    let str = String.create len in
++    let str = Bytes.create len in
+     really_input ic str 0 len;
+     if
+       (* some jpeg's start with 7f58, the 7th bit is missing *)
+-      int_of_char str.[0] lor 0x80 = 0xff &&
+-      int_of_char str.[1] lor 0x80 = 0xd8
+-      (* int_of_char str.[0] = 0xff && int_of_char str.[1] = 0xd8 *)
+-      (* && String.sub str 6 4 = "JFIF" --- strict *) then begin
++      int_of_char (Bytes.get str 0) lor 0x80 = 0xff &&
++      int_of_char (Bytes.get str 1) lor 0x80 = 0xd8
++      (* int_of_char (Bytes.get str 0) = 0xff && int_of_char (Bytes.get str 1) = 0xd8 *)
++      (* && Bytes.sub str 6 4 = "JFIF" --- strict *) then begin
+       let w, h =
+         try find_jpeg_size ic with
+         | Not_found -> -1, -1 in
+-      Pervasives.close_in ic;
++      Stdlib.close_in ic;
+       { header_width = w;
+         header_height = h;
+         header_infos = []; }
+@@ -249,7 +252,7 @@ let check_header filename =
+       raise Wrong_file_type
+   with
+   | _ ->
+-      Pervasives.close_in ic;
++      Stdlib.close_in ic;
+       raise Wrong_file_type;;
+ 
+ add_methods Jpeg
Index: pkgsrc/graphics/camlimages/patches/patch-src_jpeg.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_jpeg.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_jpeg.mli       Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_jpeg.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/jpeg.mli~      2011-06-22 18:04:32.000000000 +0000
++++ src/jpeg.mli
+@@ -37,7 +37,7 @@ type in_handle;;
+ val open_in : string -> int * int * in_handle;;
+ val open_in_thumbnail :
+   string -> Geometry.spec -> int * int * (int * int * in_handle);;
+-val read_scanline : in_handle -> string -> int -> unit;;
++val read_scanline : in_handle -> Bytes.t -> int -> unit;;
+ val close_in : in_handle -> unit;;
+   
+ type out_handle;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_jpegwrite.c
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_jpegwrite.c:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_jpegwrite.c    Sun Dec 26 05:28:23 2021
@@ -0,0 +1,46 @@
+$NetBSD: patch-src_jpegwrite.c,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Use const. Don't use const where libjpeg doesn't accept it.
+
+--- src/jpegwrite.c.orig       2011-06-22 18:04:32.000000000 +0000
++++ src/jpegwrite.c
+@@ -54,10 +54,10 @@ write_JPEG_file (value file,
+                value height, 
+                value qual)
+ {
+-  JSAMPLE *image_buffer;
++  const JSAMPLE *image_buffer;
+   int image_height;
+   int image_width;
+-  char *filename;
++  const char *filename;
+   int quality;
+ 
+   /* This struct contains the JPEG compression parameters and pointers to
+@@ -152,7 +152,7 @@ write_JPEG_file (value file,
+      * Here the array is only one element long, but you could pass
+      * more than one scanline at a time if that's more convenient.
+      */
+-    row_pointer[0] = & image_buffer[cinfo.next_scanline * row_stride];
++    row_pointer[0] = (char *) & image_buffer[cinfo.next_scanline * row_stride];
+     (void) jpeg_write_scanlines(&cinfo, row_pointer, 1);
+   }
+ 
+@@ -207,7 +207,7 @@ value open_jpeg_file_for_write_colorspac
+      value qual;
+      J_COLOR_SPACE colorspace;
+ {
+-  char *filename;
++  const char *filename;
+   int image_height;
+   int image_width;
+   int quality;
+@@ -294,7 +294,7 @@ value jpegh, buf;
+ 
+   cinfop = (struct jpeg_compress_struct *) Field( jpegh, 0 );
+ 
+-  row[0] = String_val( buf );
++  row[0] = (char *)String_val( buf );
+ 
+   jpeg_write_scanlines( cinfop, row, 1 );
+   return Val_unit;
Index: pkgsrc/graphics/camlimages/patches/patch-src_mstring.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_mstring.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_mstring.ml     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,75 @@
+$NetBSD: patch-src_mstring.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/mstring.ml.orig        2011-06-22 18:04:32.000000000 +0000
++++ src/mstring.ml
+@@ -91,12 +91,12 @@ let dec_to_hex i =
+ (* Converting a hex stored string *)
+ let hex_to_string s =
+   let len = String.length s / 2 in
+-  let res = String.create len in
++  let res = Bytes.create len in
+     for i = 0 to len - 1 do
+-      res.[i] <-
+-        char_of_int ( 16 * (hex_to_dec s.[i + i]) + hex_to_dec s.[i + i + 1])
++      Bytes.set res i
++        (char_of_int ( 16 * (hex_to_dec s.[i + i]) + hex_to_dec s.[i + i + 1]))
+       done;
+-    res;;
++    Bytes.to_string res;;
+ 
+ let gensym =
+   let cnter = ref 0 in
+@@ -125,37 +125,37 @@ let catenate_sep = String.concat;;
+ let norm_crlf lastwascr buf offs len =
+   let rpos = ref offs
+   and wpos = ref 0
+-  and dest = String.create (len + 1) (* we need one more char *)
++  and dest = Bytes.create (len + 1) (* we need one more char *)
+   and limit = offs + len - 1
+   and lastiscr = ref false in
+   if lastwascr then
+     if buf.[!rpos] = '\n' then begin
+-      dest.[!wpos] <- '\n';
++      Bytes.set dest !wpos '\n';
+       incr rpos; incr wpos
+     end else begin
+-      dest.[!wpos] <- '\n'; incr wpos
++      Bytes.set dest !wpos '\n'; incr wpos
+     end;
+ 
+   while !rpos < limit do
+     match buf.[!rpos] with
+-    | '\n' -> dest.[!wpos] <- '\n'; incr rpos; incr wpos
++    | '\n' -> Bytes.set dest !wpos '\n'; incr rpos; incr wpos
+     | '\r' ->
+       if buf.[!rpos + 1] = '\n' then begin
+-        dest.[!wpos] <- '\n'; rpos := !rpos + 2; incr wpos
++        Bytes.set dest !wpos '\n'; rpos := !rpos + 2; incr wpos
+       end else begin
+-        dest.[!wpos] <- '\n'; incr rpos; incr wpos end
+-    | c -> dest.[!wpos] <- c; incr rpos; incr wpos
++        Bytes.set dest !wpos '\n'; incr rpos; incr wpos end
++    | c -> Bytes.set dest !wpos c; incr rpos; incr wpos
+   done;
+   begin match buf.[offs+len-1] with
+-  | '\n' -> dest.[!wpos] <- '\n'; incr wpos
++  | '\n' -> Bytes.set dest !wpos '\n'; incr wpos
+   | '\r' -> lastiscr := true
+-  | c -> dest.[!wpos] <- c; incr wpos
++  | c -> Bytes.set dest !wpos c; incr wpos
+   end;
+-  String.sub dest 0 !wpos, !lastiscr;;
++  (Bytes.sub_string dest 0 !wpos, !lastiscr);;
+ 
+ let hexchar c =
+-  let s = String.make 3 '%'
++  let s = Bytes.make 3 '%'
+   and i = int_of_char c in
+-  s.[1] <- dec_to_hex (i / 16);
+-  s.[2] <- dec_to_hex (i mod 16);
+-  s;;
++  Bytes.set s 1 (dec_to_hex (i / 16));
++  Bytes.set s 2 (dec_to_hex (i mod 16));
++  Bytes.to_string s;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_oImages.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_oImages.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_oImages.ml     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_oImages.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/oImages.ml~    2011-06-22 18:04:32.000000000 +0000
++++ src/oImages.ml
+@@ -36,7 +36,7 @@ class type ['a] map = object
+   method unsafe_set : int -> int -> 'a -> unit
+   method get : int -> int -> 'a
+   method set : int -> int -> 'a -> unit
+-  method unsafe_access : int -> int -> string * int
++  method unsafe_access : int -> int -> Bytes.t * int
+ end;;
+ 
+ class type oimage = object
Index: pkgsrc/graphics/camlimages/patches/patch-src_oImages.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_oImages.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_oImages.mli    Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_oImages.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/oImages.mli~   2011-06-22 18:04:32.000000000 +0000
++++ src/oImages.mli
+@@ -39,7 +39,7 @@ class type ['a] map = object
+   method unsafe_set : int -> int -> 'a -> unit
+   method get : int -> int -> 'a
+   method set : int -> int -> 'a -> unit
+-  method unsafe_access : int -> int -> string * int
++  method unsafe_access : int -> int -> Bytes.t * int
+ end;;
+ 
+ class type oimage = object
Index: pkgsrc/graphics/camlimages/patches/patch-src_png.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_png.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_png.ml Sun Dec 26 05:28:23 2021
@@ -0,0 +1,68 @@
+$NetBSD: patch-src_png.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/png.ml.orig    2011-06-22 18:04:32.000000000 +0000
++++ src/png.ml
+@@ -53,16 +53,19 @@ let load name _opts =
+   | PNG_INDEX16 (buf,cmap) ->
+       Index16 (Index16.create_with_scanlines w h [] { max = 65535; map = cmap } (-1) buf)
+   | PNG_INDEX4 (buf,cmap) ->
+-      let buf' = Array.init h (fun _ -> String.create w) in
++      let buf' = Array.init h (fun _ -> Bytes.create w) in
+       for y = 0 to h - 1 do
+         for x = 0 to w - 1 do
+-          buf'.(y).[x] <-
++          Bytes.set (buf'.(y)) x (
+             char_of_int
+               (let c = int_of_char buf.(y).[x / 2] in
+                if x mod 2 = 0 then c lsr 4 else c mod 16)
++          )
+         done
+       done;
+-      Index8 (Index8.create_with_scanlines w h [] { max = 16; map = cmap } (-1) buf')
++      (* safe: create_with_scanlines copies the strings *)
++      let buf'' = Array.init h (fun n -> Bytes.unsafe_to_string buf'.(n)) in
++      Index8 (Index8.create_with_scanlines w h [] { max = 16; map = cmap } (-1) buf'')
+ ;;
+ 
+ let save name _opts image =
+@@ -87,27 +90,27 @@ let check_header filename =
+   let len = 24 in
+   let ic = open_in_bin filename in
+   try
+-    let str = String.create len in
++    let str = Bytes.create len in
+     really_input ic str 0 len;
+     close_in ic;
+-    if String.sub str 1 3 = "PNG" then begin
+-      if String.sub str 0 8 <> "\137PNG\013\010\026\010" then begin
++    if Bytes.sub_string str 1 3 = "PNG" then begin
++      if Bytes.sub_string str 0 8 <> "\137PNG\013\010\026\010" then begin
+           { header_width= -1;
+             header_height= -1;
+             header_infos= [Info_Corrupted]; }
+       end else begin
+           let belong str =
+-            int_of_char str.[0] lsl 24 +
+-            int_of_char str.[1] lsl 16 +
+-            int_of_char str.[2] lsl 8 +
+-            int_of_char str.[3] in
+-          let w = belong (String.sub str 16 4) in
+-          let h = belong (String.sub str 20 4) in
+-          let bdepth = Info_Depth (int_of_char str.[12]) in
++            int_of_char (Bytes.get str 0) lsl 24 +
++            int_of_char (Bytes.get str 1) lsl 16 +
++            int_of_char (Bytes.get str 2) lsl 8 +
++            int_of_char (Bytes.get str 3) in
++          let w = belong (Bytes.sub str 16 4) in
++          let h = belong (Bytes.sub str 20 4) in
++          let bdepth = Info_Depth (int_of_char (Bytes.get str 12)) in
+           let infos =
+             try
+               let colormodel =
+-                match int_of_char str.[13] with
++                match int_of_char (Bytes.get str 13) with
+                 | 0 -> Info_ColorModel Gray
+                 | 2 -> Info_ColorModel RGB
+                 | 3 -> Info_ColorModel Index
Index: pkgsrc/graphics/camlimages/patches/patch-src_rgb24.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_rgb24.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_rgb24.ml       Sun Dec 26 05:28:23 2021
@@ -0,0 +1,37 @@
+$NetBSD: patch-src_rgb24.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/rgb24.ml.orig  2011-06-22 18:04:32.000000000 +0000
++++ src/rgb24.ml
+@@ -19,15 +19,15 @@ module E = struct
+   type t = Color.rgb
+   let bytes_per_pixel = 3
+   let get str pos =
+-    { r = int_of_char str.[pos    ];
+-      g = int_of_char str.[pos + 1];
+-      b = int_of_char str.[pos + 2] }
++    { r = int_of_char (Bytes.get str (pos    ));
++      g = int_of_char (Bytes.get str (pos + 1));
++      b = int_of_char (Bytes.get str (pos + 2)) }
+   let set str pos t =
+-    str.[pos    ] <- char_of_int t.r;
+-    str.[pos + 1] <- char_of_int t.g;
+-    str.[pos + 2] <- char_of_int t.b
++    Bytes.set str (pos    ) (char_of_int t.r);
++    Bytes.set str (pos + 1) (char_of_int t.g);
++    Bytes.set str (pos + 2) (char_of_int t.b)
+   let make t =
+-    let str = String.create bytes_per_pixel in
++    let str = Bytes.create bytes_per_pixel in
+     set str 0 t;
+     str
+ end
+@@ -79,6 +79,7 @@ let rawimage = C.rawimage;;
+ let create = IMAGE.create;;
+ let make = IMAGE.make;;
+ let dump = IMAGE.dump;;
++let dumpbytes = IMAGE.dumpbytes;;
+ let unsafe_access = IMAGE.unsafe_access;;
+ let get_strip = IMAGE.get_strip;;
+ let set_strip = IMAGE.set_strip;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_rgb24.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_rgb24.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_rgb24.mli      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,22 @@
+$NetBSD: patch-src_rgb24.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/rgb24.mli.orig 2011-06-22 18:04:32.000000000 +0000
++++ src/rgb24.mli
+@@ -53,7 +53,7 @@ val unsafe_set : t -> int -> int -> elt 
+ val get_strip : t -> int -> int -> int -> string;;
+ val set_strip : t -> int -> int -> int -> string -> unit;;
+ val get_scanline : t -> int -> string;;
+-val get_scanline_ptr : t -> (int -> (string * int) * int) option;;
++val get_scanline_ptr : t -> (int -> (Bytes.t * int) * int) option;;
+ val set_scanline : t -> int -> string -> unit;;
+ val blit : t -> int -> int -> t -> int -> int -> int -> int -> unit;;
+ val map : (elt -> elt -> elt) ->
+@@ -64,4 +64,5 @@ val dump_block : t -> int -> int -> Bitm
+ val copy : t -> t;;
+ val sub : t -> int -> int -> int -> int -> t;;
+ val dump : t -> string;;
+-val unsafe_access : t -> int -> int -> string * int;;
++val dumpbytes : t -> Bytes.t;;
++val unsafe_access : t -> int -> int -> Bytes.t * int;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_rgba32.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_rgba32.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_rgba32.ml      Sun Dec 26 05:28:23 2021
@@ -0,0 +1,33 @@
+$NetBSD: patch-src_rgba32.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/rgba32.ml.orig 2011-06-22 18:04:32.000000000 +0000
++++ src/rgba32.ml
+@@ -20,17 +20,17 @@ module E = struct
+   let bytes_per_pixel = 4
+   let get str pos =
+     { color =
+-        { r = int_of_char str.[pos    ];
+-          g = int_of_char str.[pos + 1];
+-          b = int_of_char str.[pos + 2] };
+-      alpha = int_of_char str.[pos + 3] }
++        { r = int_of_char (Bytes.get str (pos    ));
++          g = int_of_char (Bytes.get str (pos + 1));
++          b = int_of_char (Bytes.get str (pos + 2)) };
++      alpha = int_of_char (Bytes.get str (pos + 3)) }
+   let set str pos t =
+-    str.[pos    ] <- char_of_int t.color.r;
+-    str.[pos + 1] <- char_of_int t.color.g;
+-    str.[pos + 2] <- char_of_int t.color.b;
+-    str.[pos + 3] <- char_of_int t.alpha
++    Bytes.set str (pos    ) (char_of_int t.color.r);
++    Bytes.set str (pos + 1) (char_of_int t.color.g);
++    Bytes.set str (pos + 2) (char_of_int t.color.b);
++    Bytes.set str (pos + 3) (char_of_int t.alpha)
+   let make t =
+-    let str = String.create bytes_per_pixel in
++    let str = Bytes.create bytes_per_pixel in
+     set str 0 t;
+     str
+ end;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_rgba32.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_rgba32.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_rgba32.mli     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_rgba32.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/rgba32.mli~    2011-06-22 18:04:32.000000000 +0000
++++ src/rgba32.mli
+@@ -37,7 +37,7 @@ val resize : (float -> unit) option -> t
+ (** Please read the comments of module [IMAGE] in file [genimage.mli]. *)
+ 
+ val dump : t -> string;;
+-val unsafe_access : t -> int -> int -> string * int;;
++val unsafe_access : t -> int -> int -> Bytes.t * int;;
+ val get_strip : t -> int -> int -> int -> string;;
+ val set_strip : t -> int -> int -> int -> string -> unit;;
+ val get_scanline : t -> int -> string;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_tiff.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_tiff.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_tiff.ml        Sun Dec 26 05:28:23 2021
@@ -0,0 +1,77 @@
+$NetBSD: patch-src_tiff.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/tiff.ml.orig   2011-06-22 18:04:32.000000000 +0000
++++ src/tiff.ml
+@@ -23,7 +23,7 @@ type in_handle;;
+ 
+ external open_in : string -> int * int * float * colormodel * in_handle
+     = "open_tiff_file_for_read";;
+-external read_scanline : in_handle -> string -> int -> unit
++external read_scanline : in_handle -> Bytes.t -> int -> unit
+     = "read_tiff_scanline";;
+ external close_in : in_handle -> unit
+     = "close_tiff_file";;
+@@ -45,23 +45,23 @@ let load name opts =
+     | RGB ->
+               let img = Rgb24.create w h in
+       Rgb24 img,
+-              String.create (w * 3)
++              Bytes.create (w * 3)
+     | CMYK ->
+       let img = Cmyk32.create w h in
+       Cmyk32 img,
+-              String.create (w * 4)
++              Bytes.create (w * 4)
+     | WHITEBLACK ->
+       let img = Index8.create w h in
+       img.Index8.colormap.map <- [| {r = 255; g = 255; b = 255};
+                                     {r = 0; g = 0; b = 0} |];
+       Index8 img,
+-      String.create ((w + 7) / 8)
++      Bytes.create ((w + 7) / 8)
+     | BLACKWHITE ->
+       let img = Index8.create w h in
+       img.Index8.colormap.map <- [| {r = 0; g = 0; b = 0};
+                                     {r = 255; g = 255; b = 255} |];
+       Index8 img,
+-      String.create ((w + 7) / 8) in
++      Bytes.create ((w + 7) / 8) in
+ 
+   let set_scanline =
+     match colormodel, img with
+@@ -81,7 +81,8 @@ let load name opts =
+ 
+   for y = 0 to h - 1 do
+     read_scanline tif buf y;
+-    set_scanline buf y;
++    (* safe: set_scanline copies it *)
++    set_scanline (Bytes.unsafe_to_string buf) y;
+     match prog with
+     | Some p -> p (float (y + 1) /. float h)
+     | None -> ()
+@@ -107,10 +108,11 @@ let check_header filename =
+   let len = 4 in
+   let ic = open_in_bin filename in
+   try
+-    let str = String.create len in
++    let str = Bytes.create len in
+     really_input ic str 0 len;
+-    Pervasives.close_in ic;
+-    match str with
++    Stdlib.close_in ic;
++    (* safe: transient and private *)
++    match Bytes.unsafe_to_string str with
+     | "MM\000\042" ->
+       { header_width = -1;
+       header_height = -1;
+@@ -122,7 +124,7 @@ let check_header filename =
+     | _ -> raise Wrong_file_type
+   with
+   | _ ->
+-      Pervasives.close_in ic;
++      Stdlib.close_in ic;
+       raise Wrong_file_type;;
+ 
+ add_methods Tiff
Index: pkgsrc/graphics/camlimages/patches/patch-src_tiff.mli
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_tiff.mli:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_tiff.mli       Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_tiff.mli,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/tiff.mli~      2011-06-22 18:04:32.000000000 +0000
++++ src/tiff.mli
+@@ -31,7 +31,7 @@ type colormodel = RGB | CMYK | WHITEBLAC
+ type in_handle;;
+ 
+ val open_in : string -> int * int * float * colormodel * in_handle;;
+-val read_scanline : in_handle -> string -> int -> unit;;
++val read_scanline : in_handle -> Bytes.t -> int -> unit;;
+ val close_in : in_handle -> unit;;
+ 
+ type out_handle;;
Index: pkgsrc/graphics/camlimages/patches/patch-src_units.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_units.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_units.ml       Sun Dec 26 05:28:23 2021
@@ -0,0 +1,15 @@
+$NetBSD: patch-src_units.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Silence nuisance warning about lowercase.
+
+--- src/units.ml~      2011-06-22 18:04:32.000000000 +0000
++++ src/units.ml
+@@ -30,7 +30,7 @@ let parse_length s = (* return in pt *)
+     let digit,unit =
+       if l > 2 then String.sub s 0 2, String.sub s (l-2) 2 else "", "" in
+     try
+-      (List.assoc (String.lowercase unit) units) *. float_of_string digit
++      (List.assoc (String.lowercase_ascii unit) units) *. float_of_string digit
+     with
+     | Not_found -> (* think it is in "pt" *)
+       float_of_string s in
Index: pkgsrc/graphics/camlimages/patches/patch-src_xpm.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_xpm.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_xpm.ml Sun Dec 26 05:28:23 2021
@@ -0,0 +1,52 @@
+$NetBSD: patch-src_xpm.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/xpm.ml.orig    2011-06-22 18:04:32.000000000 +0000
++++ src/xpm.ml
+@@ -27,31 +27,36 @@ let load file _opts =
+   (* if the colors <= 256 then we create index8,
+      otherwise create index16 *)
+   if Array.length cmap <= 256 then begin
+-    let buf = String.create (w * h) in
++    let buf = Bytes.create (w * h) in
+     for i = 0 to w * h - 1 do
+-      buf.[i] <- char_of_int imap.(i)
++      Bytes.set buf i (char_of_int imap.(i))
+     done;
++    (* safe: we just created it AND create_with copies it *)
++    let buf' = Bytes.unsafe_to_string buf in
+     Index8 (Index8.create_with w h []
+-              { map = cmap; max = 256 - 1; } transparent buf)
++              { map = cmap; max = 256 - 1; } transparent buf')
+   end else begin
+-    let buf = String.create (w * h * 2) in
++    let buf = Bytes.create (w * h * 2) in
+     for i = 0 to w * h - 1 do
+-      buf.[i * 2    ] <- char_of_int (imap.(i) / 256);
+-      buf.[i * 2 + 1] <- char_of_int (imap.(i) mod 256)
++      Bytes.set buf (i * 2    ) (char_of_int (imap.(i) / 256));
++      Bytes.set buf (i * 2 + 1) (char_of_int (imap.(i) mod 256))
+     done;
++    (* safe: we just created it AND create_with copies it *)
++    let buf' = Bytes.unsafe_to_string buf in
+     Index16 (Index16.create_with w h []
+                { map = cmap; max = 256 * 256 - 1; }
+-               transparent buf)
++               transparent buf')
+   end;;
+ 
+ let check_header filename =
+   let len = 9 in
+   let ic = open_in_bin filename in
+   try
+-    let str = String.create len in
++    let str = Bytes.create len in
+     really_input ic str 0 len;
+     close_in ic;
+-    if str = "/* XPM */" then
++    (* safe: transient and private *)
++    if Bytes.unsafe_to_string str = "/* XPM */" then
+       { header_width = -1;
+       header_height = -1;
+       header_infos = []; }
Index: pkgsrc/graphics/camlimages/patches/patch-src_xvthumb.ml
diff -u /dev/null pkgsrc/graphics/camlimages/patches/patch-src_xvthumb.ml:1.1
--- /dev/null   Sun Dec 26 05:28:23 2021
+++ pkgsrc/graphics/camlimages/patches/patch-src_xvthumb.ml     Sun Dec 26 05:28:23 2021
@@ -0,0 +1,48 @@
+$NetBSD: patch-src_xvthumb.ml,v 1.1 2021/12/26 05:28:23 dholland Exp $
+
+Update for immutable strings.
+
+--- src/xvthumb.ml.orig        2011-06-22 18:04:32.000000000 +0000
++++ src/xvthumb.ml
+@@ -19,10 +19,10 @@ open Images;;
+ (********************************************************************** load *)
+ 
+ let read_id ic =
+-  let buf = String.create 7 in
++  let buf = Bytes.create 7 in
+   try
+     really_input ic buf 0 7;
+-    if buf = "P7 332\n" then ()
++    if Bytes.to_string buf = "P7 332\n" then ()
+     else begin
+       prerr_endline "wrong header id";
+       raise Wrong_image_type
+@@ -79,10 +79,12 @@ let cmap_332 () =
+ 
+ let load_body ic w h =
+   let length = w * h in
+-  let str = String.create length in
++  let str = Bytes.create length in
+   try
+     really_input ic str 0 length;
+-    Index8.create_with w h [] (cmap_332 ()) (-1) str
++    (* safe: we just created it AND create_with copies it *)
++    let str' = Bytes.unsafe_to_string str in
++    Index8.create_with w h [] (cmap_332 ()) (-1) str'
+   with
+   | _ ->
+       prerr_endline "short";
+@@ -161,8 +163,12 @@ let create img =
+       resized
+     | Rgba32 _ | Cmyk32 _ -> failwith "RGBA and CMYK not supported"
+   in
++  (*
++   * XXX this creates and copies a batch of uninitialized data to
++   * create an uninitialized image to fill in, which is silly.
++   *)
+   let thumb = Index8.create_with nw nh [] (cmap_332 ()) (-1)
+-      (String.create (nw * nh))
++      (Bytes.unsafe_to_string (Bytes.create (nw * nh)))
+   in
+   for y = 0 to nh - 1 do
+     for x = 0 to nw - 1 do



Home | Main Index | Thread Index | Old Index