diff --git a/internal/magic/image.go b/internal/magic/image.go index 355ad94..6686f76 100644 --- a/internal/magic/image.go +++ b/internal/magic/image.go @@ -1,6 +1,9 @@ package magic -import "bytes" +import ( + "bytes" + "regexp" +) var ( // Png matches a Portable Network Graphics file. @@ -44,6 +47,21 @@ var ( Hdr = prefix([]byte("#?RADIANCE\n")) // Xpm matches X PixMap image data. Xpm = prefix([]byte{0x2F, 0x2A, 0x20, 0x58, 0x50, 0x4D, 0x20, 0x2A, 0x2F}) + // PbmAscii matches PBM ASCII image + // http://netpbm.sourceforge.net/doc/pbm.html + Pbm = re(regexp.MustCompile(`^P[14]\s+(?:#[^\n\r]*[\n\r])?\s*\d+\s+\d+\s`)) + // PgmAscii matches PGM ASCII image + // http://netpbm.sourceforge.net/doc/pgm.html + Pgm = re(regexp.MustCompile(`^P[25]\s+(?:#[^\n\r]*[\n\r])?\s*\d+\s+\d+\s`)) + // PpmAscii matches PPM ASCII image + // http://netpbm.sourceforge.net/doc/ppm.html + Ppm = re(regexp.MustCompile(`^P[36]\s+(?:#[^\n\r]*[\n\r])?\s*\d+\s+\d+\s`)) + // Pam matches PAM image + // http://netpbm.sourceforge.net/doc/pam.html + Pam = re(regexp.MustCompile(`^P7[^\n]*\n(?:\s*(?:#[^\n\r]*|(?:WIDTH|HEIGHT|DEPTH|MAXVAL)\s+\d+|TUPLTYPE\s+[^\n]+)\n)+ENDHDR[\n\r]`)) + // Pam matches PFM image + // http://netpbm.sourceforge.net/doc/pfm.html + Pfm = re(regexp.MustCompile(`^P[Ff]\s+\d+\s+\d+\s[+-]?(\d*[.])?\d+\s`)) ) func jpeg2k(sig []byte) Detector { diff --git a/internal/magic/magic.go b/internal/magic/magic.go index 466058f..c3c3611 100644 --- a/internal/magic/magic.go +++ b/internal/magic/magic.go @@ -4,6 +4,7 @@ package magic import ( "bytes" "fmt" + "regexp" ) type ( @@ -237,3 +238,11 @@ func min(a, b int) int { } return b } + +// regex creates a Detector which return true if the provided regular expression +// matches the raw input. +func re(re *regexp.Regexp) Detector { + return func(raw []byte, limit uint32) bool { + return re.Match(raw) + } +} diff --git a/internal/magic/magic_test.go b/internal/magic/magic_test.go index abf5c55..620a799 100644 --- a/internal/magic/magic_test.go +++ b/internal/magic/magic_test.go @@ -2,6 +2,7 @@ package magic import ( "io/ioutil" + "regexp" "testing" ) @@ -76,6 +77,18 @@ func TestMagic(t *testing.T) { limit: 10, res: true, }, + { + name: "regexp fail test", + detector: re(regexp.MustCompile(`qq`)), + raw: "somple string", + res: false, + }, + { + name: "regexp pass test", + detector: re(regexp.MustCompile(`\ss\w+ [0-9]{2,}`)), + raw: "sample string 12345", + res: true, + }, } for _, tt := range tCases { t.Run(tt.name, func(t *testing.T) { diff --git a/mimetype_test.go b/mimetype_test.go index f057162..e88e7d5 100644 --- a/mimetype_test.go +++ b/mimetype_test.go @@ -149,11 +149,19 @@ var files = map[string]string{ "ott.ott": "application/vnd.oasis.opendocument.text-template", "odc.odc": "application/vnd.oasis.opendocument.chart", "owl2.owl": "application/owl+xml", + "pam.pam": "image/x-portable-arbitrarymap", "pat.pat": "image/x-gimp-pat", + "pbm_ascii.pbm": "image/x-portable-bitmap", + "pbm_raw.pbm": "image/x-portable-bitmap", "pdf.pdf": "application/pdf", + "pfm.pfm": "image/x-portable-floatmap", + "pgm_ascii.pgm": "image/x-portable-graymap", + "pgm_raw.pgm": "image/x-portable-graymap", "php.php": "text/x-php", "pl.pl": "text/x-perl", "png.png": "image/png", + "ppm_ascii.ppm": "image/x-portable-pixmap", + "ppm_raw.ppm": "image/x-portable-pixmap", "ppt.ppt": "application/vnd.ms-powerpoint", "pptx.pptx": "application/vnd.openxmlformats-officedocument.presentationml.presentation", "ps.ps": "application/postscript", diff --git a/supported_mimes.md b/supported_mimes.md index 63f6d09..808339d 100644 --- a/supported_mimes.md +++ b/supported_mimes.md @@ -1,4 +1,4 @@ -## 171 Supported MIME types +## 176 Supported MIME types This file is automatically generated when running tests. Do not edit manually. Extension | MIME type | Aliases @@ -139,6 +139,11 @@ Extension | MIME type | Aliases **.glb** | model/gltf-binary | - **.avif** | image/avif | - **.cab** | application/x-installshield | - +**.ppm** | image/x-portable-pixmap | image/x-portable-anymap +**.pgm** | image/x-portable-graymap | image/x-portable-anymap +**.pbm** | image/x-portable-bitmap | image/x-portable-anymap +**.pam** | image/x-portable-arbitrarymap | - +**.pfm** | image/x-portable-floatmap | - **.txt** | text/plain | - **.html** | text/html | - **.svg** | image/svg+xml | - diff --git a/testdata/pam.pam b/testdata/pam.pam new file mode 100644 index 0000000..d1f424e Binary files /dev/null and b/testdata/pam.pam differ diff --git a/testdata/pbm_ascii.pbm b/testdata/pbm_ascii.pbm new file mode 100644 index 0000000..1b96ca9 --- /dev/null +++ b/testdata/pbm_ascii.pbm @@ -0,0 +1,4 @@ +P1 +# Created by GIMP version 2.10.30 PNM plug-in +6 10 +000010000010000010000010000010000010100010011100000000000000 \ No newline at end of file diff --git a/testdata/pbm_raw.pbm b/testdata/pbm_raw.pbm new file mode 100644 index 0000000..a13316a Binary files /dev/null and b/testdata/pbm_raw.pbm differ diff --git a/testdata/pfm.pfm b/testdata/pfm.pfm new file mode 100644 index 0000000..03c1158 Binary files /dev/null and b/testdata/pfm.pfm differ diff --git a/testdata/pgm_ascii.pgm b/testdata/pgm_ascii.pgm new file mode 100644 index 0000000..9d7330a --- /dev/null +++ b/testdata/pgm_ascii.pgm @@ -0,0 +1,64 @@ +P2 +# Created by GIMP version 2.10.30 PNM plug-in +6 10 +255 +255 +255 +255 +255 +0 +255 +255 +255 +255 +255 +0 +255 +255 +255 +255 +255 +0 +255 +255 +255 +255 +255 +0 +255 +255 +255 +255 +255 +0 +255 +255 +255 +255 +255 +0 +255 +0 +255 +255 +255 +0 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 diff --git a/testdata/pgm_raw.pgm b/testdata/pgm_raw.pgm new file mode 100644 index 0000000..4442f48 Binary files /dev/null and b/testdata/pgm_raw.pgm differ diff --git a/testdata/ppm_ascii.ppm b/testdata/ppm_ascii.ppm new file mode 100644 index 0000000..7868c6a --- /dev/null +++ b/testdata/ppm_ascii.ppm @@ -0,0 +1,184 @@ +P3 +# Created by GIMP version 2.10.30 PNM plug-in +6 10 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +0 +0 +0 +255 +255 +255 +255 +255 +255 +0 +0 +0 +0 +0 +0 +0 +0 +0 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 +255 diff --git a/testdata/ppm_raw.ppm b/testdata/ppm_raw.ppm new file mode 100644 index 0000000..4996fa6 Binary files /dev/null and b/testdata/ppm_raw.ppm differ diff --git a/tree.go b/tree.go index 980624f..2405e8a 100644 --- a/tree.go +++ b/tree.go @@ -24,7 +24,7 @@ var root = newMIME("application/octet-stream", "", gzip, class, swf, crx, ttf, woff, woff2, otf, ttc, eot, wasm, shx, dbf, dcm, rar, djvu, mobi, lit, bpg, sqlite3, dwg, nes, lnk, macho, qcp, icns, heic, heicSeq, heif, heifSeq, hdr, mrc, mdb, accdb, zstd, cab, rpm, xz, lzip, - torrent, cpio, tzif, xcf, pat, gbr, glb, avif, cabIS, + torrent, cpio, tzif, xcf, pat, gbr, glb, avif, cabIS, ppm, pgm, pbm, pam, pfm, // Keep text last because it is the slowest check text, ) @@ -254,4 +254,9 @@ var ( gbr = newMIME("image/x-gimp-gbr", ".gbr", magic.Gbr) xfdf = newMIME("application/vnd.adobe.xfdf", ".xfdf", magic.Xfdf) glb = newMIME("model/gltf-binary", ".glb", magic.Glb) + pbm = newMIME("image/x-portable-bitmap", ".pbm", magic.Pbm).alias("image/x-portable-anymap") + pgm = newMIME("image/x-portable-graymap", ".pgm", magic.Pgm).alias("image/x-portable-anymap") + ppm = newMIME("image/x-portable-pixmap", ".ppm", magic.Ppm).alias("image/x-portable-anymap") + pam = newMIME("image/x-portable-arbitrarymap", ".pam", magic.Pam) + pfm = newMIME("image/x-portable-floatmap", ".pfm", magic.Pfm) )