MFV r276568:

Update file to 5.22.

MFC after:	2 weeks
This commit is contained in:
Xin LI 2015-01-02 21:20:02 +00:00
commit 4460e5b02d
36 changed files with 797 additions and 562 deletions

View File

@ -1,3 +1,29 @@
2015-01-02 15:15 Christos Zoulas <christos@zoulas.com>
* release 5.22
2015-01-01 12:01 Christos Zoulas <christos@zoulas.com>
* add indirect relative for TIFF/Exif
2014-12-16 18:10 Christos Zoulas <christos@zoulas.com>
* restructure elf note printing to avoid repeated messages
* add note limit, suggested by Alexander Cherepanov
2014-12-16 16:53 Christos Zoulas <christos@zoulas.com>
* Bail out on partial pread()'s (Alexander Cherepanov)
* Fix incorrect bounds check in file_printable (Alexander Cherepanov)
2014-12-11 20:01 Christos Zoulas <christos@zoulas.com>
* PR/405: ignore SIGPIPE from uncompress programs
* change printable -> file_printable and use it in
more places for safety
* in ELF, instead of "(uses dynamic libraries)" when PT_INTERP
is present print the interpreter name.
2014-12-10 20:01 Christos Zoulas <christos@zoulas.com>
* release 5.21
@ -23,6 +49,8 @@
- reduce the number of recursion levels from 20 to 10
- preserve error messages in indirect magic handling
This is tracked as CVE-2014-8116 and CVE-2014-8117
2014-11-12 10:30 Christos Zoulas <christos@zoulas.com>
* fix bogus free in the user buffer case.

View File

@ -1,4 +1,4 @@
# Makefile.in generated by automake 1.14.1 from Makefile.am.
# Makefile.in generated by automake 1.14 from Makefile.am.
# @configure_input@
# Copyright (C) 1994-2013 Free Software Foundation, Inc.
@ -618,10 +618,9 @@ distcheck: dist
&& dc_destdir="$${TMPDIR-/tmp}/am-dc-$$$$/" \
&& am__cwd=`pwd` \
&& $(am__cd) $(distdir)/_build \
&& ../configure \
&& ../configure --srcdir=.. --prefix="$$dc_install_base" \
$(AM_DISTCHECK_CONFIGURE_FLAGS) \
$(DISTCHECK_CONFIGURE_FLAGS) \
--srcdir=.. --prefix="$$dc_install_base" \
&& $(MAKE) $(AM_MAKEFLAGS) \
&& $(MAKE) $(AM_MAKEFLAGS) dvi \
&& $(MAKE) $(AM_MAKEFLAGS) check \

View File

@ -1,6 +1,6 @@
## README for file(1) Command ##
@(#) $File: README,v 1.48 2014/03/07 13:55:30 christos Exp $
@(#) $File: README,v 1.49 2015/01/02 20:23:04 christos Exp $
Mailing List: file@mx.gw.com
Mailing List archives: http://mx.gw.com/pipermail/file/
@ -25,8 +25,8 @@ A public read-only git repository of the same sources is available at:
https://github.com/file/file
The major changes for 5.x are CDF file parsing, indirect magic, and
overhaul in mime and ascii encoding handling.
The major changes for 5.x are CDF file parsing, indirect magic, name/use
(recursion) and overhaul in mime and ascii encoding handling.
The major feature of 4.x is the refactoring of the code into a library,
and the re-write of the file command in terms of that library. The library
@ -67,33 +67,41 @@ in magic(5) format please, to the maintainer, Christos Zoulas.
COPYING - read this first.
README - read this second (you are currently reading this file).
INSTALL - read on how to install
src/apprentice.c - parses /etc/magic to learn magic
src/asctime_r.c - replacement for OS's that don't have it.
src/apptype.c - used for OS/2 specific application type magic
src/asprintf.c - replacement for OS's that don't have it.
src/ascmagic.c - third & last set of tests, based on hardwired assumptions.
src/asctime_r.c - for systems that don't have it.
src/asprintf.c - for systems that don't have it.
src/cdf.c - parser for Microsoft Compound Document Files
src/asctime_r.c - replacement for OS's that don't have it.
src/asprintf.c - replacement for OS's that don't have it.
src/cdf.[ch] - parser for Microsoft Compound Document Files
src/cdf_time.c - time converter for CDF.
src/compress.c - handles decompressing files to look inside.
src/ctime_r.c - for systems that don't have it.
src/ctime_r.c - replacement for OS's that don't have it.
src/elfclass.h - common code for elf 32/64.
src/encoding.c - handles unicode encodings
src/file.c - the main program
src/file.h - header file
src/file_opts.h - list of options
src/fmtcheck.c - replacement for OS's that don't have it.
src/fsmagic.c - first set of tests the program runs, based on filesystem info
src/funcs.c - utilility functions
src/getopt_long.c - for systems that don't have it.
src/getline.c - for systems that don't have it.
src/getline.c - replacement for OS's that don't have it.
src/getopt_long.c - replacement for OS's that don't have it.
src/is_tar.c, tar.h - knows about tarchives (courtesy John Gilmore).
src/names.h - header file for ascmagic.c
src/magic.h.in - source file for magic.h
src/magic.c - the libmagic api
src/pread.c - replacement for OS's that don't have it.
src/print.c - print results, errors, warnings.
src/readcdf.c - CDF wrapper.
src/readelf.[ch] - Stand-alone elf parsing code.
src/softmagic.c - 2nd set of tests, based on /etc/magic
src/strlcat.c - for systems that don't have it.
src/strlcpy.c - for systems that don't have it.
src/mygetopt.h - replacement for OS's that don't have it.
src/strcasestr.c - replacement for OS's that don't have it.
src/strlcat.c - replacement for OS's that don't have it.
src/strlcpy.c - replacement for OS's that don't have it.
src/tar.h - tar file definitions
src/vasprintf.c - for systems that don't have it.
doc/file.man - man page for the command
doc/magic.man - man page for the magic file, courtesy Guy Harris.

View File

@ -1,4 +1,4 @@
# generated automatically by aclocal 1.14.1 -*- Autoconf -*-
# generated automatically by aclocal 1.14 -*- Autoconf -*-
# Copyright (C) 1996-2013 Free Software Foundation, Inc.
@ -21,7 +21,7 @@ If you have problems, you may need to regenerate the build system entirely.
To do so, use the procedure documented by the package, typically 'autoreconf'.])])
# visibility.m4 serial 5 (gettext-0.18.2)
dnl Copyright (C) 2005, 2008, 2010-2014 Free Software Foundation, Inc.
dnl Copyright (C) 2005, 2008, 2010-2013 Free Software Foundation, Inc.
dnl This file is free software; the Free Software Foundation
dnl gives unlimited permission to copy and/or distribute it,
dnl with or without modifications, as long as this notice is preserved.
@ -113,7 +113,7 @@ AC_DEFUN([AM_AUTOMAKE_VERSION],
[am__api_version='1.14'
dnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to
dnl require some minimum version. Point them to the right macro.
m4_if([$1], [1.14.1], [],
m4_if([$1], [1.14], [],
[AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl
])
@ -129,7 +129,7 @@ m4_define([_AM_AUTOCONF_VERSION], [])
# Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.
# This function is AC_REQUIREd by AM_INIT_AUTOMAKE.
AC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],
[AM_AUTOMAKE_VERSION([1.14.1])dnl
[AM_AUTOMAKE_VERSION([1.14])dnl
m4_ifndef([AC_AUTOCONF_VERSION],
[m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl
_AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])

View File

@ -1,6 +1,6 @@
#! /bin/sh
# Guess values for system-dependent variables and create Makefiles.
# Generated by GNU Autoconf 2.69 for file 5.21.
# Generated by GNU Autoconf 2.69 for file 5.22.
#
# Report bugs to <christos@astron.com>.
#
@ -590,8 +590,8 @@ MAKEFLAGS=
# Identity of this package.
PACKAGE_NAME='file'
PACKAGE_TARNAME='file'
PACKAGE_VERSION='5.21'
PACKAGE_STRING='file 5.21'
PACKAGE_VERSION='5.22'
PACKAGE_STRING='file 5.22'
PACKAGE_BUGREPORT='christos@astron.com'
PACKAGE_URL=''
@ -1327,7 +1327,7 @@ if test "$ac_init_help" = "long"; then
# Omit some internal or obsolete options to make the list less imposing.
# This message is too long to be a string in the A/UX 3.1 sh.
cat <<_ACEOF
\`configure' configures file 5.21 to adapt to many kinds of systems.
\`configure' configures file 5.22 to adapt to many kinds of systems.
Usage: $0 [OPTION]... [VAR=VALUE]...
@ -1397,7 +1397,7 @@ fi
if test -n "$ac_init_help"; then
case $ac_init_help in
short | recursive ) echo "Configuration of file 5.21:";;
short | recursive ) echo "Configuration of file 5.22:";;
esac
cat <<\_ACEOF
@ -1507,7 +1507,7 @@ fi
test -n "$ac_init_help" && exit $ac_status
if $ac_init_version; then
cat <<\_ACEOF
file configure 5.21
file configure 5.22
generated by GNU Autoconf 2.69
Copyright (C) 2012 Free Software Foundation, Inc.
@ -2163,7 +2163,7 @@ cat >config.log <<_ACEOF
This file contains any messages produced by compilers while
running configure, to aid debugging if configure makes a mistake.
It was created by file $as_me 5.21, which was
It was created by file $as_me 5.22, which was
generated by GNU Autoconf 2.69. Invocation command line was
$ $0 $@
@ -3029,7 +3029,7 @@ fi
# Define the identity of the package.
PACKAGE='file'
VERSION='5.21'
VERSION='5.22'
cat >>confdefs.h <<_ACEOF
@ -14998,7 +14998,7 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1
# report actual input values of CONFIG_FILES etc. instead of their
# values after options handling.
ac_log="
This file was extended by file $as_me 5.21, which was
This file was extended by file $as_me 5.22, which was
generated by GNU Autoconf 2.69. Invocation command line was
CONFIG_FILES = $CONFIG_FILES
@ -15064,7 +15064,7 @@ _ACEOF
cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1
ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"
ac_cs_version="\\
file config.status 5.21
file config.status 5.22
configured by $0, generated by GNU Autoconf 2.69,
with options \\"\$ac_cs_config\\"

View File

@ -1,5 +1,5 @@
dnl Process this file with autoconf to produce a configure script.
AC_INIT([file],[5.21],[christos@astron.com])
AC_INIT([file],[5.22],[christos@astron.com])
AM_INIT_AUTOMAKE([subdir-objects foreign])
m4_ifdef([AM_SILENT_RULES], [AM_SILENT_RULES([yes])])

View File

@ -1,4 +1,4 @@
# Makefile.in generated by automake 1.14.1 from Makefile.am.
# Makefile.in generated by automake 1.14 from Makefile.am.
# @configure_input@
# Copyright (C) 1994-2013 Free Software Foundation, Inc.

View File

@ -1,5 +1,5 @@
.\" $File: file.man,v 1.110 2014/11/28 02:46:39 christos Exp $
.Dd November 27, 2014
.\" $File: file.man,v 1.111 2014/12/16 23:18:40 christos Exp $
.Dd December 16, 2014
.Dt FILE __CSECTION__
.Os
.Sh NAME
@ -310,6 +310,7 @@ Set various parameter limits.
.It Sy "Name" Ta Sy "Default" Ta Sy "Explanation"
.It Li indir Ta 15 Ta recursion limit for indirect magic
.It Li name Ta 30 Ta use count limit for name/use magic
.It Li elf_notes Ta 256 Ta max ELF notes processed
.It Li elf_phnum Ta 128 Ta max ELF program sections processed
.It Li elf_shnum Ta 32768 Ta max ELF sections processed
.El

View File

@ -1,4 +1,4 @@
.\" $File: libmagic.man,v 1.33 2014/11/28 02:46:39 christos Exp $
.\" $File: libmagic.man,v 1.34 2014/12/16 23:18:40 christos Exp $
.\"
.\" Copyright (c) Christos Zoulas 2003.
.\" All Rights Reserved.
@ -25,7 +25,7 @@
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
.Dd November 27, 2014
.Dd December 16, 2014
.Dt LIBMAGIC 3
.Os
.Sh NAME
@ -284,6 +284,7 @@ library.
.It Sy "Parameter" Ta Sy "Type" Ta Sy "Default"
.It Li MAGIC_PARAM_INDIR_MAX Ta size_t Ta 15
.It Li MAGIC_PARAM_NAME_MAX Ta size_t Ta 30
.It Li MAGIC_PARAM_ELF_NOTES_MAX Ta size_t Ta 256
.It Li MAGIC_PARAM_ELF_PHNUM_MAX Ta size_t Ta 128
.It Li MAGIC_PARAM_ELF_SHNUM_MAX Ta size_t Ta 32768
.El
@ -303,12 +304,16 @@ The
parameter controls the maximum number of calls for name/use.
.Pp
The
.Dv MAGIC_PARAM_NOTES_MAX
parameter controls how many ELF notes will be processed.
.Pp
The
.Dv MAGIC_PARAM_PHNUM_MAX
parameter controls how many elf program sections will be processed.
parameter controls how many ELF program sections will be processed.
.Pp
The
.Dv MAGIC_PARAM_SHNUM_MAX
parameter controls how many elf sections will be processed.
parameter controls how many ELF sections will be processed.
.Pp
The
.Fn magic_version

View File

@ -1,5 +1,5 @@
.\" $File: magic.man,v 1.84 2014/06/03 19:01:34 christos Exp $
.Dd June 3, 2014
.\" $File: magic.man,v 1.85 2015/01/01 17:07:34 christos Exp $
.Dd January 1, 2015
.Dt MAGIC __FSECTION__
.Os
.\" install as magic.4 on USG, magic.5 on V7, Berkeley and Linux systems.
@ -200,6 +200,11 @@ interpreted as a UNIX-style date, but interpreted as local time rather
than UTC.
.It Dv indirect
Starting at the given offset, consult the magic database again.
The offset of th
.Dv indirect
magic is by default absolute in the file, but one can specify
.Dv /r
to indicate that the offset is relative from the beginning of the entry.
.It Dv name
Define a
.Dq named

View File

@ -2,6 +2,6 @@
#------------------------------------------------------------------------------
# Localstuff: file(1) magic for locally observed files
#
# $File: Localstuff,v 1.5 2007/01/12 17:38:27 christos Exp $
# $File: Localstuff,v 1.4 2003/03/23 04:17:27 christos Exp $
# Add any locally observed files here. Remember:
# text if readable, executable if runnable binary, data if unreadable.

View File

@ -1,6 +1,6 @@
#------------------------------------------------------------------------------
# $File: cafebabe,v 1.16 2014/04/30 21:41:02 christos Exp $
# $File: cafebabe,v 1.17 2015/01/01 17:07:00 christos Exp $
# Cafe Babes unite!
#
# Since Java bytecode and Mach-O universal binaries have the same magic number,
@ -45,7 +45,7 @@
0 name mach-o \b [
>0 use mach-o-cpu \b
>&(8.L) indirect \b:
>(8.L) indirect \b:
>0 belong x \b]
0 belong 0xcafebabe

View File

@ -1,5 +1,5 @@
#------------------------------------------------------------------------------
# $File: filesystems,v 1.107 2014/12/03 18:02:52 christos Exp $
# $File: filesystems,v 1.108 2015/01/01 17:43:47 christos Exp $
# filesystems: file(1) magic for different filesystems
#
0 name partid
@ -260,6 +260,13 @@
>>(11.s-2) uleshort 0xAA55 DOS/MBR boot sector
# for sector sizes with 512 or more Bytes
>0x1FE leshort 0xAA55 DOS/MBR boot sector
# keep old DOS/MBR boot sector as dummy for mbr and bootloader displaying
# only for sector sizes with 512 or more Bytes
0x1FE leshort 0xAA55 DOS/MBR boot sector
#
# to display information (50) before DOS BPB (strength=70) and after DOS floppy (120) like in old file version
!:strength +65
>2 string OSBS OS/BS MBR
# added by Joerg Jenderek at Feb 2013 according to http://thestarman.pcministry.com/asm/mbr/
# and http://en.wikipedia.org/wiki/Master_Boot_Record

View File

@ -1,6 +1,6 @@
#------------------------------------------------------------------------------
# $File: images,v 1.97 2014/12/08 16:06:19 christos Exp $
# $File: images,v 1.102 2015/01/02 02:36:35 christos Exp $
# images: file(1) magic for image formats (see also "iff", and "c-lang" for
# XPM bitmaps)
#
@ -115,7 +115,7 @@
# never changed. The TIFF specification recommends testing for it.
0 string MM\x00\x2a TIFF image data, big-endian
!:mime image/tiff
>(4.L) use tiff_ifd
>(4.L) use \^tiff_ifd
0 string II\x2a\x00 TIFF image data, little-endian
!:mime image/tiff
>(4.l) use tiff_ifd
@ -125,54 +125,57 @@
>2 use tiff_entry
0 name tiff_entry
# NewSubFileType
>0 leshort 0xfe
>>12 use tiff_entry
>0 leshort 0x100
>>4 lelong 1
>>>12 use tiff_entry
>>>8 lelong x \b, width=%d
>>>8 leshort x \b, width=%d
>0 leshort 0x101
>>4 lelong 1
>>>8 lelong x \b, height=%d
>>>8 leshort x \b, height=%d
>>>12 use tiff_entry
>0 leshort 0x102
>>8 lelong x \b, bps=%d
>>8 leshort x \b, bps=%d
>>12 use tiff_entry
>0 leshort 0x103
>>4 lelong 1 \b, compression=
>>>8 lelong 1 \bnone
>>>8 lelong 2 \bhuffman
>>>8 lelong 3 \bbi-level group 3
>>>8 lelong 4 \bbi-level group 4
>>>8 lelong 5 \bLZW
>>>8 lelong 6 \bJPEG (old)
>>>8 lelong 7 \bJPEG
>>>8 lelong 8 \bdeflate
>>>8 lelong 9 \bJBIG, ITU-T T.85
>>>8 lelong 0xa \bJBIG, ITU-T T.43
>>>8 lelong 0x7ffe \bNeXT RLE 2-bit
>>>8 lelong 0x8005 \bPackBits (Macintosh RLE)
>>>8 lelong 0x8029 \bThunderscan RLE
>>>8 lelong 0x807f \bRasterPadding (CT or MP)
>>>8 lelong 0x8080 \bRLE (Line Work)
>>>8 lelong 0x8081 \bRLE (High-Res Cont-Tone)
>>>8 lelong 0x8082 \bRLE (Binary Line Work)
>>>8 lelong 0x80b2 \bDeflate (PKZIP)
>>>8 lelong 0x80b3 \bKodak DCS
>>>8 lelong 0x8765 \bJBIG
>>>8 lelong 0x8798 \bJPEG2000
>>>8 lelong 0x8799 \bNikon NEF Compressed
>>>8 leshort 1 \bnone
>>>8 leshort 2 \bhuffman
>>>8 leshort 3 \bbi-level group 3
>>>8 leshort 4 \bbi-level group 4
>>>8 leshort 5 \bLZW
>>>8 leshort 6 \bJPEG (old)
>>>8 leshort 7 \bJPEG
>>>8 leshort 8 \bdeflate
>>>8 leshort 9 \bJBIG, ITU-T T.85
>>>8 leshort 0xa \bJBIG, ITU-T T.43
>>>8 leshort 0x7ffe \bNeXT RLE 2-bit
>>>8 leshort 0x8005 \bPackBits (Macintosh RLE)
>>>8 leshort 0x8029 \bThunderscan RLE
>>>8 leshort 0x807f \bRasterPadding (CT or MP)
>>>8 leshort 0x8080 \bRLE (Line Work)
>>>8 leshort 0x8081 \bRLE (High-Res Cont-Tone)
>>>8 leshort 0x8082 \bRLE (Binary Line Work)
>>>8 leshort 0x80b2 \bDeflate (PKZIP)
>>>8 leshort 0x80b3 \bKodak DCS
>>>8 leshort 0x8765 \bJBIG
>>>8 leshort 0x8798 \bJPEG2000
>>>8 leshort 0x8799 \bNikon NEF Compressed
>>>8 default x
>>>>8 lelong x \b(unknown 0x%x)
>>>>8 leshort x \b(unknown 0x%x)
>>>12 use tiff_entry
>0 leshort 0x106 \b, PhotometricIntepretation=
>>8 lelong 0 \bWhiteIsZero
>>8 lelong 1 \bBlackIsZero
>>8 lelong 2 \bRGB
>>8 lelong 3 \bRGB Palette
>>8 lelong 4 \bTransparency Mask
>>8 lelong 5 \bCMYK
>>8 lelong 6 \bYCbCr
>>8 lelong 8 \bCIELab
>>>8 lelong x \b(unknown=0x%x)
>>8 leshort 0 \bWhiteIsZero
>>8 leshort 1 \bBlackIsZero
>>8 leshort 2 \bRGB
>>8 leshort 3 \bRGB Palette
>>8 leshort 4 \bTransparency Mask
>>8 leshort 5 \bCMYK
>>8 leshort 6 \bYCbCr
>>8 leshort 8 \bCIELab
>>>8 leshort x \b(unknown=0x%x)
>>12 use tiff_entry
# FillOrder
>0 leshort 0x10a
@ -186,21 +189,79 @@
>0 leshort 0x10e
>>(8.l) string x \b, description=%s
>>>12 use tiff_entry
# Make
>0 leshort 0x10f
>>(8.l) string x \b, manufacturer=%s
>>>12 use tiff_entry
# Model
>0 leshort 0x110
>>(8.l) string x \b, model=%s
>>>12 use tiff_entry
# StripOffsets
>0 leshort 0x111
>>12 use tiff_entry
# NewSubFileType
>0 leshort 0xfe
# Orientation
>0 leshort 0x112 \b, orientation=
>>8 leshort 1 \bupper-left
>>8 leshort 3 \blower-right
>>8 leshort 6 \bupper-right
>>8 leshort 8 \blower-left
>>8 leshort 9 \bundefined
>>8 default x
>>>8 leshort x \b[*%d*]
>>12 use tiff_entry
# XResolution
>0 leshort 0x11a
>>8 lelong x \b, xresolution=%d
>>12 use tiff_entry
# YResolution
>0 leshort 0x11b
>>8 lelong x \b, yresolution=%d
>>12 use tiff_entry
# ResolutionUnit
>0 leshort 0x128
>>8 leshort x \b, resolutionunit=%d
>>12 use tiff_entry
# Software
>0 leshort 0x131
>>(8.l) string x \b, software=%s
>>12 use tiff_entry
# Datetime
>0 leshort 0x132
>>(8.l) string x \b, datetime=%s
>>>12 use tiff_entry
>>12 use tiff_entry
# HostComputer
>0 leshort 0x13c
>>(8.l) string x \b, hostcomputer=%s
>>>12 use tiff_entry
>>12 use tiff_entry
# WhitePoint
>0 leshort 0x13e
>>12 use tiff_entry
# PrimaryChromaticities
>0 leshort 0x13f
>>12 use tiff_entry
# YCbCrCoefficients
>0 leshort 0x211
>>12 use tiff_entry
# YCbCrPositioning
>0 leshort 0x213
>>12 use tiff_entry
# ReferenceBlackWhite
>0 leshort 0x214
>>12 use tiff_entry
# Copyright
>0 leshort 0x8298
>>(8.l) string x \b, copyright=%s
>>12 use tiff_entry
# ExifOffset
>0 leshort 0x8769
>>12 use tiff_entry
# GPS IFD
>0 leshort 0x8825 \b, GPS-Data
>>12 use tiff_entry
#>0 leshort x \b, unknown=0x%x
#>>12 use tiff_entry
0 string MM\x00\x2b Big TIFF image data, big-endian
!:mime image/tiff

View File

@ -1,6 +1,6 @@
#------------------------------------------------------------------------------
# $File: jpeg,v 1.21 2014/09/12 20:47:00 christos Exp $
# $File: jpeg,v 1.25 2015/01/02 16:56:50 christos Exp $
# JPEG images
# SunOS 5.5.1 had
#
@ -31,98 +31,9 @@
# Next, show thumbnail info, if it exists:
>>18 byte !0 \b, thumbnail %dx
>>>19 byte x \b%d
# EXIF moved down here to avoid reporting a bogus version number,
# and EXIF version number printing added.
# - Patrik R=E5dman <patrik+file-magic@iki.fi>
>6 string Exif \b, EXIF standard
# Look for EXIF IFD offset in IFD 0, and then look for EXIF version tag in EXIF IFD.
# All possible combinations of entries have to be enumerated, since no looping
# is possible. And both endians are possible...
# The combinations included below are from real-world JPEGs.
# Little-endian
>>12 string II
# IFD 0 Entry #5:
>>>70 leshort 0x8769
# EXIF IFD Entry #1:
>>>>(78.l+14) leshort 0x9000
>>>>>(78.l+23) byte x %c
>>>>>(78.l+24) byte x \b.%c
>>>>>(78.l+25) byte !0x30 \b%c
# IFD 0 Entry #9:
>>>118 leshort 0x8769
# EXIF IFD Entry #3:
>>>>(126.l+38) leshort 0x9000
>>>>>(126.l+47) byte x %c
>>>>>(126.l+48) byte x \b.%c
>>>>>(126.l+49) byte !0x30 \b%c
# IFD 0 Entry #10
>>>130 leshort 0x8769
# EXIF IFD Entry #3:
>>>>(138.l+38) leshort 0x9000
>>>>>(138.l+47) byte x %c
>>>>>(138.l+48) byte x \b.%c
>>>>>(138.l+49) byte !0x30 \b%c
# EXIF IFD Entry #4:
>>>>(138.l+50) leshort 0x9000
>>>>>(138.l+59) byte x %c
>>>>>(138.l+60) byte x \b.%c
>>>>>(138.l+61) byte !0x30 \b%c
# EXIF IFD Entry #5:
>>>>(138.l+62) leshort 0x9000
>>>>>(138.l+71) byte x %c
>>>>>(138.l+72) byte x \b.%c
>>>>>(138.l+73) byte !0x30 \b%c
# IFD 0 Entry #11
>>>142 leshort 0x8769
# EXIF IFD Entry #3:
>>>>(150.l+38) leshort 0x9000
>>>>>(150.l+47) byte x %c
>>>>>(150.l+48) byte x \b.%c
>>>>>(150.l+49) byte !0x30 \b%c
# EXIF IFD Entry #4:
>>>>(150.l+50) leshort 0x9000
>>>>>(150.l+59) byte x %c
>>>>>(150.l+60) byte x \b.%c
>>>>>(150.l+61) byte !0x30 \b%c
# EXIF IFD Entry #5:
>>>>(150.l+62) leshort 0x9000
>>>>>(150.l+71) byte x %c
>>>>>(150.l+72) byte x \b.%c
>>>>>(150.l+73) byte !0x30 \b%c
# Big-endian
>>12 string MM
# IFD 0 Entry #9:
>>>118 beshort 0x8769
# EXIF IFD Entry #1:
>>>>(126.L+14) beshort 0x9000
>>>>>(126.L+23) byte x %c
>>>>>(126.L+24) byte x \b.%c
>>>>>(126.L+25) byte !0x30 \b%c
# EXIF IFD Entry #3:
>>>>(126.L+38) beshort 0x9000
>>>>>(126.L+47) byte x %c
>>>>>(126.L+48) byte x \b.%c
>>>>>(126.L+49) byte !0x30 \b%c
# IFD 0 Entry #10
>>>130 beshort 0x8769
# EXIF IFD Entry #3:
>>>>(138.L+38) beshort 0x9000
>>>>>(138.L+47) byte x %c
>>>>>(138.L+48) byte x \b.%c
>>>>>(138.L+49) byte !0x30 \b%c
# EXIF IFD Entry #5:
>>>>(138.L+62) beshort 0x9000
>>>>>(138.L+71) byte x %c
>>>>>(138.L+72) byte x \b.%c
>>>>>(138.L+73) byte !0x30 \b%c
# IFD 0 Entry #11
>>>142 beshort 0x8769
# EXIF IFD Entry #4:
>>>>(150.L+50) beshort 0x9000
>>>>>(150.L+59) byte x %c
>>>>>(150.L+60) byte x \b.%c
>>>>>(150.L+61) byte !0x30 \b%c
>6 string Exif \b, Exif standard: [
>>12 indirect/r x
>>12 string x \b]
# Jump to the first segment
>(4.S+4) use jpeg_segment
@ -158,6 +69,12 @@
>0 beshort 0xFFC4
>>(2.S+2) use jpeg_segment
>0 beshort 0xFFE1
#>>(2.S+2) use jpeg_segment
>>4 string Exif \b, Exif Standard: [
>>>10 indirect/r x
>>>10 string x \b]
# Application specific markers
>0 beshort&0xFFE0 =0xFFE0
>>(2.S+2) use jpeg_segment
@ -170,6 +87,9 @@
>0 beshort&0xFFD0 =0xFFD0
>>(2.S+2) use jpeg_segment
#>0 beshort x unknown 0x%x
#>>(2.S+2) use jpeg_segment
# HSI is Handmade Software's proprietary JPEG encoding scheme
0 string hsi1 JPEG image data, HSI proprietary

View File

@ -0,0 +1,19 @@
#------------------------------------------------------------------------------
# $File: qt,v 1.2 2014/12/16 19:49:29 christos Exp $
# qt: file(1) magic for Qt
# http://doc.qt.io/qt-5/resources.html
0 string \<!DOCTYPE\040RCC\> Qt Resource Collection file
# https://qt.gitorious.org/qt/qtbase/source/\
# 5367fa356233da4c0f28172a8f817791525f5457:\
# src/tools/rcc/rcc.cpp#L840
0 string qres\0\0 Qt Binary Resource file
0 search/1024 The\040Resource\040Compiler\040for\040Qt Qt C-code resource file
# https://qt.gitorious.org/qt/qtbase/source/\
# 5367fa356233da4c0f28172a8f817791525f5457:\
# src/corelib/kernel/qtranslator.cpp#L62
0 string \x3c\xb8\x64\x18\xca\xef\x9c\x95
>8 string \xcd\x21\x1c\xbf\x60\xa1\xbd\xdd Qt Translation file

View File

@ -1,5 +1,5 @@
#
# $File: Makefile.am,v 1.100 2014/12/10 18:45:43 christos Exp $
# $File: Makefile.am,v 1.101 2014/12/12 16:48:39 christos Exp $
#
MAGIC_FRAGMENT_BASE = Magdir
MAGIC_DIR = $(top_srcdir)/magic
@ -198,6 +198,7 @@ $(MAGIC_FRAGMENT_DIR)/pulsar \
$(MAGIC_FRAGMENT_DIR)/pwsafe \
$(MAGIC_FRAGMENT_DIR)/pyramid \
$(MAGIC_FRAGMENT_DIR)/python \
$(MAGIC_FRAGMENT_DIR)/qt \
$(MAGIC_FRAGMENT_DIR)/revision \
$(MAGIC_FRAGMENT_DIR)/riff \
$(MAGIC_FRAGMENT_DIR)/rpm \

View File

@ -1,4 +1,4 @@
# Makefile.in generated by automake 1.14.1 from Makefile.am.
# Makefile.in generated by automake 1.14 from Makefile.am.
# @configure_input@
# Copyright (C) 1994-2013 Free Software Foundation, Inc.
@ -262,7 +262,7 @@ top_builddir = @top_builddir@
top_srcdir = @top_srcdir@
#
# $File: Makefile.am,v 1.100 2014/12/10 18:45:43 christos Exp $
# $File: Makefile.am,v 1.101 2014/12/12 16:48:39 christos Exp $
#
MAGIC_FRAGMENT_BASE = Magdir
MAGIC_DIR = $(top_srcdir)/magic
@ -459,6 +459,7 @@ $(MAGIC_FRAGMENT_DIR)/pulsar \
$(MAGIC_FRAGMENT_DIR)/pwsafe \
$(MAGIC_FRAGMENT_DIR)/pyramid \
$(MAGIC_FRAGMENT_DIR)/python \
$(MAGIC_FRAGMENT_DIR)/qt \
$(MAGIC_FRAGMENT_DIR)/revision \
$(MAGIC_FRAGMENT_DIR)/riff \
$(MAGIC_FRAGMENT_DIR)/rpm \

View File

@ -1,7 +1,7 @@
#! /bin/sh
# Common wrapper for a few potentially missing GNU programs.
scriptversion=2013-10-28.13; # UTC
scriptversion=2012-06-26.16; # UTC
# Copyright (C) 1996-2013 Free Software Foundation, Inc.
# Originally written by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.
@ -160,7 +160,7 @@ give_advice ()
;;
autom4te*)
echo "You might have modified some maintainer files that require"
echo "the 'autom4te' program to be rebuilt."
echo "the 'automa4te' program to be rebuilt."
program_details 'autom4te'
;;
bison*|yacc*)

View File

@ -1,4 +1,4 @@
# Makefile.in generated by automake 1.14.1 from Makefile.am.
# Makefile.in generated by automake 1.14 from Makefile.am.
# @configure_input@
# Copyright (C) 1994-2013 Free Software Foundation, Inc.

View File

@ -1,4 +1,4 @@
# Makefile.in generated by automake 1.14.1 from Makefile.am.
# Makefile.in generated by automake 1.14 from Makefile.am.
# @configure_input@
# Copyright (C) 1994-2013 Free Software Foundation, Inc.
@ -81,9 +81,9 @@ build_triplet = @build@
host_triplet = @host@
bin_PROGRAMS = file$(EXEEXT)
subdir = src
DIST_COMMON = $(srcdir)/Makefile.in $(srcdir)/Makefile.am strcasestr.c \
pread.c strlcpy.c vasprintf.c getopt_long.c asctime_r.c \
strlcat.c ctime_r.c getline.c asprintf.c fmtcheck.c \
DIST_COMMON = $(srcdir)/Makefile.in $(srcdir)/Makefile.am ctime_r.c \
vasprintf.c asctime_r.c asprintf.c strcasestr.c pread.c \
getline.c strlcpy.c strlcat.c fmtcheck.c getopt_long.c \
$(top_srcdir)/depcomp $(include_HEADERS)
ACLOCAL_M4 = $(top_srcdir)/aclocal.m4
am__aclocal_m4_deps = $(top_srcdir)/m4/libtool.m4 \

View File

@ -32,7 +32,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: apprentice.c,v 1.227 2014/11/28 02:46:39 christos Exp $")
FILE_RCSID("@(#)$File: apprentice.c,v 1.229 2015/01/01 17:07:34 christos Exp $")
#endif /* lint */
#include "magic.h"
@ -528,6 +528,7 @@ file_ms_alloc(int flags)
ms->name_max = FILE_NAME_MAX;
ms->elf_shnum_max = FILE_ELF_SHNUM_MAX;
ms->elf_phnum_max = FILE_ELF_PHNUM_MAX;
ms->elf_notes_max = FILE_ELF_NOTES_MAX;
return ms;
free:
free(ms);
@ -1604,6 +1605,145 @@ check_cond(struct magic_set *ms, int cond, uint32_t cont_level)
}
#endif /* ENABLE_CONDITIONALS */
private int
parse_indirect_modifier(struct magic_set *ms, struct magic *m, const char **lp)
{
const char *l = *lp;
while (!isspace((unsigned char)*++l))
switch (*l) {
case CHAR_INDIRECT_RELATIVE:
m->str_flags |= INDIRECT_RELATIVE;
break;
default:
if (ms->flags & MAGIC_CHECK)
file_magwarn(ms, "indirect modifier `%c' "
"invalid", *l);
*lp = l;
return -1;
}
*lp = l;
return 0;
}
private void
parse_op_modifier(struct magic_set *ms, struct magic *m, const char **lp,
int op)
{
const char *l = *lp;
char *t;
uint64_t val;
++l;
m->mask_op |= op;
val = (uint64_t)strtoull(l, &t, 0);
l = t;
m->num_mask = file_signextend(ms, m, val);
eatsize(&l);
*lp = l;
}
private int
parse_string_modifier(struct magic_set *ms, struct magic *m, const char **lp)
{
const char *l = *lp;
char *t;
int have_range = 0;
while (!isspace((unsigned char)*++l)) {
switch (*l) {
case '0': case '1': case '2':
case '3': case '4': case '5':
case '6': case '7': case '8':
case '9':
if (have_range && (ms->flags & MAGIC_CHECK))
file_magwarn(ms, "multiple ranges");
have_range = 1;
m->str_range = CAST(uint32_t, strtoul(l, &t, 0));
if (m->str_range == 0)
file_magwarn(ms, "zero range");
l = t - 1;
break;
case CHAR_COMPACT_WHITESPACE:
m->str_flags |= STRING_COMPACT_WHITESPACE;
break;
case CHAR_COMPACT_OPTIONAL_WHITESPACE:
m->str_flags |= STRING_COMPACT_OPTIONAL_WHITESPACE;
break;
case CHAR_IGNORE_LOWERCASE:
m->str_flags |= STRING_IGNORE_LOWERCASE;
break;
case CHAR_IGNORE_UPPERCASE:
m->str_flags |= STRING_IGNORE_UPPERCASE;
break;
case CHAR_REGEX_OFFSET_START:
m->str_flags |= REGEX_OFFSET_START;
break;
case CHAR_BINTEST:
m->str_flags |= STRING_BINTEST;
break;
case CHAR_TEXTTEST:
m->str_flags |= STRING_TEXTTEST;
break;
case CHAR_TRIM:
m->str_flags |= STRING_TRIM;
break;
case CHAR_PSTRING_1_LE:
#define SET_LENGTH(a) m->str_flags = (m->str_flags & ~PSTRING_LEN) | (a)
if (m->type != FILE_PSTRING)
goto bad;
SET_LENGTH(PSTRING_1_LE);
break;
case CHAR_PSTRING_2_BE:
if (m->type != FILE_PSTRING)
goto bad;
SET_LENGTH(PSTRING_2_BE);
break;
case CHAR_PSTRING_2_LE:
if (m->type != FILE_PSTRING)
goto bad;
SET_LENGTH(PSTRING_2_LE);
break;
case CHAR_PSTRING_4_BE:
if (m->type != FILE_PSTRING)
goto bad;
SET_LENGTH(PSTRING_4_BE);
break;
case CHAR_PSTRING_4_LE:
switch (m->type) {
case FILE_PSTRING:
case FILE_REGEX:
break;
default:
goto bad;
}
SET_LENGTH(PSTRING_4_LE);
break;
case CHAR_PSTRING_LENGTH_INCLUDES_ITSELF:
if (m->type != FILE_PSTRING)
goto bad;
m->str_flags |= PSTRING_LENGTH_INCLUDES_ITSELF;
break;
default:
bad:
if (ms->flags & MAGIC_CHECK)
file_magwarn(ms, "string modifier `%c' "
"invalid", *l);
goto out;
}
/* allow multiple '/' for readability */
if (l[1] == '/' && !isspace((unsigned char)l[2]))
l++;
}
if (string_modifier_check(ms, m) == -1)
goto out;
*lp = l;
return 0;
out:
*lp = l;
return -1;
}
/*
* parse one line from magic file, put into magic[index++] if valid
*/
@ -1873,118 +2013,27 @@ parse(struct magic_set *ms, struct magic_entry *me, const char *line,
m->str_range = 0;
m->str_flags = m->type == FILE_PSTRING ? PSTRING_1_LE : 0;
if ((op = get_op(*l)) != -1) {
if (!IS_STRING(m->type)) {
uint64_t val;
++l;
m->mask_op |= op;
val = (uint64_t)strtoull(l, &t, 0);
l = t;
m->num_mask = file_signextend(ms, m, val);
eatsize(&l);
}
else if (op == FILE_OPDIVIDE) {
int have_range = 0;
while (!isspace((unsigned char)*++l)) {
switch (*l) {
case '0': case '1': case '2':
case '3': case '4': case '5':
case '6': case '7': case '8':
case '9':
if (have_range &&
(ms->flags & MAGIC_CHECK))
file_magwarn(ms,
"multiple ranges");
have_range = 1;
m->str_range = CAST(uint32_t,
strtoul(l, &t, 0));
if (m->str_range == 0)
file_magwarn(ms,
"zero range");
l = t - 1;
break;
case CHAR_COMPACT_WHITESPACE:
m->str_flags |=
STRING_COMPACT_WHITESPACE;
break;
case CHAR_COMPACT_OPTIONAL_WHITESPACE:
m->str_flags |=
STRING_COMPACT_OPTIONAL_WHITESPACE;
break;
case CHAR_IGNORE_LOWERCASE:
m->str_flags |= STRING_IGNORE_LOWERCASE;
break;
case CHAR_IGNORE_UPPERCASE:
m->str_flags |= STRING_IGNORE_UPPERCASE;
break;
case CHAR_REGEX_OFFSET_START:
m->str_flags |= REGEX_OFFSET_START;
break;
case CHAR_BINTEST:
m->str_flags |= STRING_BINTEST;
break;
case CHAR_TEXTTEST:
m->str_flags |= STRING_TEXTTEST;
break;
case CHAR_TRIM:
m->str_flags |= STRING_TRIM;
break;
case CHAR_PSTRING_1_LE:
if (m->type != FILE_PSTRING)
goto bad;
m->str_flags = (m->str_flags & ~PSTRING_LEN) | PSTRING_1_LE;
break;
case CHAR_PSTRING_2_BE:
if (m->type != FILE_PSTRING)
goto bad;
m->str_flags = (m->str_flags & ~PSTRING_LEN) | PSTRING_2_BE;
break;
case CHAR_PSTRING_2_LE:
if (m->type != FILE_PSTRING)
goto bad;
m->str_flags = (m->str_flags & ~PSTRING_LEN) | PSTRING_2_LE;
break;
case CHAR_PSTRING_4_BE:
if (m->type != FILE_PSTRING)
goto bad;
m->str_flags = (m->str_flags & ~PSTRING_LEN) | PSTRING_4_BE;
break;
case CHAR_PSTRING_4_LE:
switch (m->type) {
case FILE_PSTRING:
case FILE_REGEX:
break;
default:
goto bad;
}
m->str_flags = (m->str_flags & ~PSTRING_LEN) | PSTRING_4_LE;
break;
case CHAR_PSTRING_LENGTH_INCLUDES_ITSELF:
if (m->type != FILE_PSTRING)
goto bad;
m->str_flags |= PSTRING_LENGTH_INCLUDES_ITSELF;
break;
default:
bad:
if (ms->flags & MAGIC_CHECK)
file_magwarn(ms,
"string extension `%c' "
"invalid", *l);
return -1;
}
/* allow multiple '/' for readability */
if (l[1] == '/' &&
!isspace((unsigned char)l[2]))
l++;
}
if (string_modifier_check(ms, m) == -1)
if (IS_STRING(m->type)) {
int r;
if (op != FILE_OPDIVIDE) {
if (ms->flags & MAGIC_CHECK)
file_magwarn(ms,
"invalid string/indirect op: "
"`%c'", *t);
return -1;
}
else {
if (ms->flags & MAGIC_CHECK)
file_magwarn(ms, "invalid string op: %c", *t);
return -1;
}
}
if (m->type == FILE_INDIRECT)
r = parse_indirect_modifier(ms, m, &l);
else
r = parse_string_modifier(ms, m, &l);
if (r == -1)
return -1;
} else
parse_op_modifier(ms, m, &l, op);
}
/*
* We used to set mask to all 1's here, instead let's just not do
* anything if mask = 0 (unless you have a better idea)

View File

@ -35,7 +35,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: compress.c,v 1.75 2014/12/04 15:56:46 christos Exp $")
FILE_RCSID("@(#)$File: compress.c,v 1.77 2014/12/12 16:33:01 christos Exp $")
#endif
#include "magic.h"
@ -45,6 +45,7 @@ FILE_RCSID("@(#)$File: compress.c,v 1.75 2014/12/04 15:56:46 christos Exp $")
#endif
#include <string.h>
#include <errno.h>
#include <signal.h>
#if !defined(__MINGW32__) && !defined(WIN32)
#include <sys/ioctl.h>
#endif
@ -103,10 +104,12 @@ file_zmagic(struct magic_set *ms, int fd, const char *name,
size_t i, nsz;
int rv = 0;
int mime = ms->flags & MAGIC_MIME;
sig_t osigpipe;
if ((ms->flags & MAGIC_COMPRESS) == 0)
return 0;
osigpipe = signal(SIGPIPE, SIG_IGN);
for (i = 0; i < ncompr; i++) {
if (nbytes < compr[i].maglen)
continue;
@ -133,6 +136,7 @@ file_zmagic(struct magic_set *ms, int fd, const char *name,
}
}
error:
(void)signal(SIGPIPE, osigpipe);
free(newbuf);
ms->flags |= MAGIC_COMPRESS;
return rv;
@ -508,11 +512,16 @@ uncompressbuf(struct magic_set *ms, int fd, size_t method,
strerror(errno));
#endif
n = NODATA;
} else if (!WIFEXITED(status) || WEXITSTATUS(status) != 0) {
} else if (!WIFEXITED(status)) {
#ifdef DEBUG
(void)fprintf(stderr, "Child status (0x%x)\n", status);
(void)fprintf(stderr, "Child not exited (0x%x)\n",
status);
#endif
} else if (WEXITSTATUS(status) != 0) {
#ifdef DEBUG
(void)fprintf(stderr, "Child exited (0x%d)\n",
WEXITSTATUS(status));
#endif
n = NODATA;
}
(void) close(fdin[0]);

View File

@ -32,17 +32,18 @@
swap = (u.c[sizeof(int32_t) - 1] + 1) != elfhdr.e_ident[EI_DATA];
type = elf_getu16(swap, elfhdr.e_type);
notecount = ms->elf_notes_max;
switch (type) {
#ifdef ELFCORE
case ET_CORE:
phnum = elf_getu16(swap, elfhdr.e_phnum);
if (phnum > ms->elf_phnum_max)
return toomany(ms, "program", phnum);
return toomany(ms, "program headers", phnum);
flags |= FLAGS_IS_CORE;
if (dophn_core(ms, clazz, swap, fd,
(off_t)elf_getu(swap, elfhdr.e_phoff), phnum,
(size_t)elf_getu16(swap, elfhdr.e_phentsize),
fsize, &flags) == -1)
fsize, &flags, &notecount) == -1)
return -1;
break;
#endif
@ -57,22 +58,25 @@
if (dophn_exec(ms, clazz, swap, fd,
(off_t)elf_getu(swap, elfhdr.e_phoff), phnum,
(size_t)elf_getu16(swap, elfhdr.e_phentsize),
fsize, &flags, shnum) == -1)
fsize, shnum, &flags, &notecount) == -1)
return -1;
/*FALLTHROUGH*/
case ET_REL:
shnum = elf_getu16(swap, elfhdr.e_shnum);
if (shnum > ms->elf_shnum_max)
return toomany(ms, "section", shnum);
return toomany(ms, "section headers", shnum);
if (doshn(ms, clazz, swap, fd,
(off_t)elf_getu(swap, elfhdr.e_shoff), shnum,
(size_t)elf_getu16(swap, elfhdr.e_shentsize),
fsize, &flags, elf_getu16(swap, elfhdr.e_machine),
(int)elf_getu16(swap, elfhdr.e_shstrndx)) == -1)
fsize, elf_getu16(swap, elfhdr.e_machine),
(int)elf_getu16(swap, elfhdr.e_shstrndx),
&flags, &notecount) == -1)
return -1;
break;
default:
break;
}
if (notecount == 0)
return toomany(ms, "notes", ms->elf_notes_max);
return 1;

View File

@ -32,7 +32,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: file.c,v 1.159 2014/11/28 02:46:39 christos Exp $")
FILE_RCSID("@(#)$File: file.c,v 1.160 2014/12/16 23:18:40 christos Exp $")
#endif /* lint */
#include "magic.h"
@ -125,6 +125,7 @@ private struct {
{ "name", MAGIC_PARAM_NAME_MAX, 0 },
{ "elf_phnum", MAGIC_PARAM_ELF_PHNUM_MAX, 0 },
{ "elf_shnum", MAGIC_PARAM_ELF_SHNUM_MAX, 0 },
{ "elf_notes", MAGIC_PARAM_ELF_NOTES_MAX, 0 },
};
private char *progname; /* used throughout */

View File

@ -27,7 +27,7 @@
*/
/*
* file.h - definitions for file(1) program
* @(#)$File: file.h,v 1.161 2014/12/04 15:56:46 christos Exp $
* @(#)$File: file.h,v 1.164 2015/01/01 17:07:34 christos Exp $
*/
#ifndef __file_h__
@ -234,6 +234,7 @@ struct magic {
(t) == FILE_LESTRING16 || \
(t) == FILE_REGEX || \
(t) == FILE_SEARCH || \
(t) == FILE_INDIRECT || \
(t) == FILE_NAME || \
(t) == FILE_USE)
@ -346,6 +347,8 @@ struct magic {
#define STRING_IGNORE_CASE (STRING_IGNORE_LOWERCASE|STRING_IGNORE_UPPERCASE)
#define STRING_DEFAULT_RANGE 100
#define INDIRECT_RELATIVE BIT(0)
#define CHAR_INDIRECT_RELATIVE 'r'
/* list of magic entries */
struct mlist {
@ -407,10 +410,12 @@ struct magic_set {
uint16_t name_max;
uint16_t elf_shnum_max;
uint16_t elf_phnum_max;
uint16_t elf_notes_max;
#define FILE_INDIR_MAX 15
#define FILE_NAME_MAX 30
#define FILE_ELF_SHNUM_MAX 32768
#define FILE_ELF_PHNUM_MAX 128
#define FILE_ELF_NOTES_MAX 256
};
/* Type for Unicode characters */
@ -476,6 +481,7 @@ protected int file_looks_utf8(const unsigned char *, size_t, unichar *,
size_t *);
protected size_t file_pstring_length_size(const struct magic *);
protected size_t file_pstring_get_length(const struct magic *, const char *);
protected char * file_printable(char *, size_t, const char *);
#ifdef __EMX__
protected int file_os2_apptype(struct magic_set *, const char *, const void *,
size_t);

View File

@ -43,8 +43,13 @@ OPT('0', "print0", 0, " terminate filenames with ASCII NUL\n")
#if defined(HAVE_UTIME) || defined(HAVE_UTIMES)
OPT('p', "preserve-date", 0, " preserve access times on files\n")
#endif
OPT('P', "parameter", 0, " set file engine parameter limits\n"
" indir 15 recursion limit for indirection\n"
" name 30 use limit for name/use magic\n"
" elf_notes 256 max ELF notes processed\n"
" elf_phnum 128 max ELF prog sections processed\n"
" elf_shnum 32768 max ELF sections processed\n")
OPT('r', "raw", 0, " don't translate unprintable chars to \\ooo\n")
OPT('R', "recursion", 0, " set maximum recursion level\n")
OPT('s', "special-files", 0, " treat special (block/char devices) files as\n"
" ordinary ones\n")
OPT('C', "compile", 0, " compile file specified by -m\n")

View File

@ -27,7 +27,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: funcs.c,v 1.77 2014/11/28 02:46:39 christos Exp $")
FILE_RCSID("@(#)$File: funcs.c,v 1.79 2014/12/16 20:52:49 christos Exp $")
#endif /* lint */
#include "magic.h"
@ -531,3 +531,28 @@ file_pop_buffer(struct magic_set *ms, file_pushbuf_t *pb)
free(pb);
return rbuf;
}
/*
* convert string to ascii printable format.
*/
protected char *
file_printable(char *buf, size_t bufsiz, const char *str)
{
char *ptr, *eptr;
const unsigned char *s = (const unsigned char *)str;
for (ptr = buf, eptr = ptr + bufsiz - 1; ptr < eptr && *s; s++) {
if (isprint(*s)) {
*ptr++ = *s;
continue;
}
if (ptr >= eptr - 3)
break;
*ptr++ = '\\';
*ptr++ = ((*s >> 6) & 7) + '0';
*ptr++ = ((*s >> 3) & 7) + '0';
*ptr++ = ((*s >> 0) & 7) + '0';
}
*ptr = '\0';
return buf;
}

View File

@ -80,7 +80,7 @@ getdelim(char **buf, size_t *bufsiz, int delimiter, FILE *fp)
}
}
ssize_t
public ssize_t
getline(char **buf, size_t *bufsiz, FILE *fp)
{
return getdelim(buf, bufsiz, '\n', fp);

View File

@ -33,7 +33,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: magic.c,v 1.90 2014/12/04 15:56:46 christos Exp $")
FILE_RCSID("@(#)$File: magic.c,v 1.91 2014/12/16 23:18:40 christos Exp $")
#endif /* lint */
#include "magic.h"
@ -554,6 +554,9 @@ magic_setparam(struct magic_set *ms, int param, const void *val)
case MAGIC_PARAM_ELF_SHNUM_MAX:
ms->elf_shnum_max = *(const size_t *)val;
return 0;
case MAGIC_PARAM_ELF_NOTES_MAX:
ms->elf_notes_max = *(const size_t *)val;
return 0;
default:
errno = EINVAL;
return -1;
@ -576,6 +579,9 @@ magic_getparam(struct magic_set *ms, int param, void *val)
case MAGIC_PARAM_ELF_SHNUM_MAX:
*(size_t *)val = ms->elf_shnum_max;
return 0;
case MAGIC_PARAM_ELF_NOTES_MAX:
*(size_t *)val = ms->elf_notes_max;
return 0;
default:
errno = EINVAL;
return -1;

View File

@ -107,6 +107,7 @@ int magic_errno(magic_t);
#define MAGIC_PARAM_NAME_MAX 1
#define MAGIC_PARAM_ELF_PHNUM_MAX 2
#define MAGIC_PARAM_ELF_SHNUM_MAX 3
#define MAGIC_PARAM_ELF_NOTES_MAX 4
int magic_setparam(magic_t, int, const void *);
int magic_getparam(magic_t, int, void *);

View File

@ -107,6 +107,7 @@ int magic_errno(magic_t);
#define MAGIC_PARAM_NAME_MAX 1
#define MAGIC_PARAM_ELF_PHNUM_MAX 2
#define MAGIC_PARAM_ELF_SHNUM_MAX 3
#define MAGIC_PARAM_ELF_NOTES_MAX 4
int magic_setparam(magic_t, int, const void *);
int magic_getparam(magic_t, int, void *);

View File

@ -27,7 +27,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: readelf.c,v 1.111 2014/12/09 02:47:45 christos Exp $")
FILE_RCSID("@(#)$File: readelf.c,v 1.117 2014/12/16 23:29:42 christos Exp $")
#endif
#ifdef BUILTIN_ELF
@ -43,14 +43,14 @@ FILE_RCSID("@(#)$File: readelf.c,v 1.111 2014/12/09 02:47:45 christos Exp $")
#ifdef ELFCORE
private int dophn_core(struct magic_set *, int, int, int, off_t, int, size_t,
off_t, int *);
off_t, int *, uint16_t *);
#endif
private int dophn_exec(struct magic_set *, int, int, int, off_t, int, size_t,
off_t, int *, int);
off_t, int, int *, uint16_t *);
private int doshn(struct magic_set *, int, int, int, off_t, int, size_t,
off_t, int *, int, int);
off_t, int, int, int *, uint16_t *);
private size_t donote(struct magic_set *, void *, size_t, size_t, int,
int, size_t, int *);
int, size_t, int *, uint16_t *);
#define ELF_ALIGN(a) ((((a) + align - 1) / align) * align)
@ -67,7 +67,7 @@ private uint64_t getu64(int, uint64_t);
private int
toomany(struct magic_set *ms, const char *name, uint16_t num)
{
if (file_printf(ms, ", too many %s header sections (%u)", name, num
if (file_printf(ms, ", too many %s (%u)", name, num
) == -1)
return -1;
return 0;
@ -293,15 +293,19 @@ private const char os_style_names[][8] = {
"NetBSD",
};
#define FLAGS_DID_CORE 0x01
#define FLAGS_DID_NOTE 0x02
#define FLAGS_DID_BUILD_ID 0x04
#define FLAGS_DID_CORE_STYLE 0x08
#define FLAGS_IS_CORE 0x10
#define FLAGS_DID_CORE 0x001
#define FLAGS_DID_OS_NOTE 0x002
#define FLAGS_DID_BUILD_ID 0x004
#define FLAGS_DID_CORE_STYLE 0x008
#define FLAGS_DID_NETBSD_PAX 0x010
#define FLAGS_DID_NETBSD_MARCH 0x020
#define FLAGS_DID_NETBSD_CMODEL 0x040
#define FLAGS_DID_NETBSD_UNKNOWN 0x080
#define FLAGS_IS_CORE 0x100
private int
dophn_core(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
int num, size_t size, off_t fsize, int *flags)
int num, size_t size, off_t fsize, int *flags, uint16_t *notecount)
{
Elf32_Phdr ph32;
Elf64_Phdr ph64;
@ -319,7 +323,7 @@ dophn_core(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
* Loop through all the program headers.
*/
for ( ; num; num--) {
if (pread(fd, xph_addr, xph_sizeof, off) == -1) {
if (pread(fd, xph_addr, xph_sizeof, off) < (ssize_t)xph_sizeof) {
file_badread(ms);
return -1;
}
@ -347,7 +351,7 @@ dophn_core(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
if (offset >= (size_t)bufsize)
break;
offset = donote(ms, nbuf, offset, (size_t)bufsize,
clazz, swap, 4, flags);
clazz, swap, 4, flags, notecount);
if (offset == 0)
break;
@ -477,132 +481,127 @@ do_note_freebsd_version(struct magic_set *ms, int swap, void *v)
}
}
private size_t
donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
int clazz, int swap, size_t align, int *flags)
private int
do_bid_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
int swap __attribute__((__unused__)), uint32_t namesz, uint32_t descsz,
size_t noff, size_t doff, int *flags)
{
Elf32_Nhdr nh32;
Elf64_Nhdr nh64;
size_t noff, doff;
#ifdef ELFCORE
int os_style = -1;
#endif
uint32_t namesz, descsz;
unsigned char *nbuf = CAST(unsigned char *, vbuf);
if (xnh_sizeof + offset > size) {
/*
* We're out of note headers.
*/
return xnh_sizeof + offset;
}
(void)memcpy(xnh_addr, &nbuf[offset], xnh_sizeof);
offset += xnh_sizeof;
namesz = xnh_namesz;
descsz = xnh_descsz;
if ((namesz == 0) && (descsz == 0)) {
/*
* We're out of note headers.
*/
return (offset >= size) ? offset : size;
}
if (namesz & 0x80000000) {
(void)file_printf(ms, ", bad note name size 0x%lx",
(unsigned long)namesz);
return 0;
}
if (descsz & 0x80000000) {
(void)file_printf(ms, ", bad note description size 0x%lx",
(unsigned long)descsz);
return 0;
}
noff = offset;
doff = ELF_ALIGN(offset + namesz);
if (offset + namesz > size) {
/*
* We're past the end of the buffer.
*/
return doff;
}
offset = ELF_ALIGN(doff + descsz);
if (doff + descsz > size) {
/*
* We're past the end of the buffer.
*/
return (offset >= size) ? offset : size;
}
if ((*flags & (FLAGS_DID_NOTE|FLAGS_DID_BUILD_ID)) ==
(FLAGS_DID_NOTE|FLAGS_DID_BUILD_ID))
goto core;
if (namesz == 5 && strcmp((char *)&nbuf[noff], "SuSE") == 0 &&
xnh_type == NT_GNU_VERSION && descsz == 2) {
file_printf(ms, ", for SuSE %d.%d", nbuf[doff], nbuf[doff + 1]);
}
if (namesz == 4 && strcmp((char *)&nbuf[noff], "GNU") == 0 &&
xnh_type == NT_GNU_VERSION && descsz == 16) {
type == NT_GNU_BUILD_ID && (descsz == 16 || descsz == 20)) {
uint8_t desc[20];
uint32_t i;
*flags |= FLAGS_DID_BUILD_ID;
if (file_printf(ms, ", BuildID[%s]=", descsz == 16 ? "md5/uuid" :
"sha1") == -1)
return 1;
(void)memcpy(desc, &nbuf[doff], descsz);
for (i = 0; i < descsz; i++)
if (file_printf(ms, "%02x", desc[i]) == -1)
return 1;
return 1;
}
return 0;
}
private int
do_os_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
int swap, uint32_t namesz, uint32_t descsz,
size_t noff, size_t doff, int *flags)
{
if (namesz == 5 && strcmp((char *)&nbuf[noff], "SuSE") == 0 &&
type == NT_GNU_VERSION && descsz == 2) {
*flags |= FLAGS_DID_OS_NOTE;
file_printf(ms, ", for SuSE %d.%d", nbuf[doff], nbuf[doff + 1]);
return 1;
}
if (namesz == 4 && strcmp((char *)&nbuf[noff], "GNU") == 0 &&
type == NT_GNU_VERSION && descsz == 16) {
uint32_t desc[4];
(void)memcpy(desc, &nbuf[doff], sizeof(desc));
*flags |= FLAGS_DID_OS_NOTE;
if (file_printf(ms, ", for GNU/") == -1)
return size;
return 1;
switch (elf_getu32(swap, desc[0])) {
case GNU_OS_LINUX:
if (file_printf(ms, "Linux") == -1)
return size;
return 1;
break;
case GNU_OS_HURD:
if (file_printf(ms, "Hurd") == -1)
return size;
return 1;
break;
case GNU_OS_SOLARIS:
if (file_printf(ms, "Solaris") == -1)
return size;
return 1;
break;
case GNU_OS_KFREEBSD:
if (file_printf(ms, "kFreeBSD") == -1)
return size;
return 1;
break;
case GNU_OS_KNETBSD:
if (file_printf(ms, "kNetBSD") == -1)
return size;
return 1;
break;
default:
if (file_printf(ms, "<unknown>") == -1)
return size;
return 1;
}
if (file_printf(ms, " %d.%d.%d", elf_getu32(swap, desc[1]),
elf_getu32(swap, desc[2]), elf_getu32(swap, desc[3])) == -1)
return size;
*flags |= FLAGS_DID_NOTE;
return size;
return 1;
return 1;
}
if (namesz == 4 && strcmp((char *)&nbuf[noff], "GNU") == 0 &&
xnh_type == NT_GNU_BUILD_ID && (descsz == 16 || descsz == 20)) {
uint8_t desc[20];
uint32_t i;
if (file_printf(ms, ", BuildID[%s]=", descsz == 16 ? "md5/uuid" :
"sha1") == -1)
return size;
(void)memcpy(desc, &nbuf[doff], descsz);
for (i = 0; i < descsz; i++)
if (file_printf(ms, "%02x", desc[i]) == -1)
return size;
*flags |= FLAGS_DID_BUILD_ID;
if (namesz == 7 && strcmp((char *)&nbuf[noff], "NetBSD") == 0) {
if (type == NT_NETBSD_VERSION && descsz == 4) {
*flags |= FLAGS_DID_OS_NOTE;
do_note_netbsd_version(ms, swap, &nbuf[doff]);
return 1;
}
}
if (namesz == 8 && strcmp((char *)&nbuf[noff], "FreeBSD") == 0) {
if (type == NT_FREEBSD_VERSION && descsz == 4) {
*flags |= FLAGS_DID_OS_NOTE;
do_note_freebsd_version(ms, swap, &nbuf[doff]);
return 1;
}
}
if (namesz == 8 && strcmp((char *)&nbuf[noff], "OpenBSD") == 0 &&
type == NT_OPENBSD_VERSION && descsz == 4) {
*flags |= FLAGS_DID_OS_NOTE;
if (file_printf(ms, ", for OpenBSD") == -1)
return 1;
/* Content of note is always 0 */
return 1;
}
if (namesz == 10 && strcmp((char *)&nbuf[noff], "DragonFly") == 0 &&
type == NT_DRAGONFLY_VERSION && descsz == 4) {
uint32_t desc;
*flags |= FLAGS_DID_OS_NOTE;
if (file_printf(ms, ", for DragonFly") == -1)
return 1;
(void)memcpy(&desc, &nbuf[doff], sizeof(desc));
desc = elf_getu32(swap, desc);
if (file_printf(ms, " %d.%d.%d", desc / 100000,
desc / 10000 % 10, desc % 10000) == -1)
return 1;
return 1;
}
return 0;
}
private int
do_pax_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
int swap, uint32_t namesz, uint32_t descsz,
size_t noff, size_t doff, int *flags)
{
if (namesz == 4 && strcmp((char *)&nbuf[noff], "PaX") == 0 &&
xnh_type == NT_NETBSD_PAX && descsz == 4) {
type == NT_NETBSD_PAX && descsz == 4) {
static const char *pax[] = {
"+mprotect",
"-mprotect",
@ -615,80 +614,32 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
size_t i;
int did = 0;
*flags |= FLAGS_DID_NETBSD_PAX;
(void)memcpy(&desc, &nbuf[doff], sizeof(desc));
desc = elf_getu32(swap, desc);
if (desc && file_printf(ms, ", PaX: ") == -1)
return size;
return 1;
for (i = 0; i < __arraycount(pax); i++) {
if (((1 << i) & desc) == 0)
continue;
if (file_printf(ms, "%s%s", did++ ? "," : "",
pax[i]) == -1)
return size;
return 1;
}
return 1;
}
return 0;
}
if (namesz == 7 && strcmp((char *)&nbuf[noff], "NetBSD") == 0) {
switch (xnh_type) {
case NT_NETBSD_VERSION:
if (descsz == 4) {
do_note_netbsd_version(ms, swap, &nbuf[doff]);
*flags |= FLAGS_DID_NOTE;
return size;
}
break;
case NT_NETBSD_MARCH:
if (file_printf(ms, ", compiled for: %.*s", (int)descsz,
(const char *)&nbuf[doff]) == -1)
return size;
break;
case NT_NETBSD_CMODEL:
if (file_printf(ms, ", compiler model: %.*s",
(int)descsz, (const char *)&nbuf[doff]) == -1)
return size;
break;
default:
if (file_printf(ms, ", note=%u", xnh_type) == -1)
return size;
break;
}
return size;
}
if (namesz == 8 && strcmp((char *)&nbuf[noff], "FreeBSD") == 0) {
if (xnh_type == NT_FREEBSD_VERSION && descsz == 4) {
do_note_freebsd_version(ms, swap, &nbuf[doff]);
*flags |= FLAGS_DID_NOTE;
return size;
}
}
if (namesz == 8 && strcmp((char *)&nbuf[noff], "OpenBSD") == 0 &&
xnh_type == NT_OPENBSD_VERSION && descsz == 4) {
if (file_printf(ms, ", for OpenBSD") == -1)
return size;
/* Content of note is always 0 */
*flags |= FLAGS_DID_NOTE;
return size;
}
if (namesz == 10 && strcmp((char *)&nbuf[noff], "DragonFly") == 0 &&
xnh_type == NT_DRAGONFLY_VERSION && descsz == 4) {
uint32_t desc;
if (file_printf(ms, ", for DragonFly") == -1)
return size;
(void)memcpy(&desc, &nbuf[doff], sizeof(desc));
desc = elf_getu32(swap, desc);
if (file_printf(ms, " %d.%d.%d", desc / 100000,
desc / 10000 % 10, desc % 10000) == -1)
return size;
*flags |= FLAGS_DID_NOTE;
return size;
}
core:
private int
do_core_note(struct magic_set *ms, unsigned char *nbuf, uint32_t type,
int swap, uint32_t namesz, uint32_t descsz,
size_t noff, size_t doff, int *flags, size_t size, int clazz)
{
#ifdef ELFCORE
int os_style = -1;
/*
* Sigh. The 2.0.36 kernel in Debian 2.1, at
* least, doesn't correctly implement name
@ -717,20 +668,17 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
os_style = OS_STYLE_NETBSD;
}
#ifdef ELFCORE
if ((*flags & FLAGS_DID_CORE) != 0)
return size;
if (os_style != -1 && (*flags & FLAGS_DID_CORE_STYLE) == 0) {
if (file_printf(ms, ", %s-style", os_style_names[os_style])
== -1)
return size;
return 1;
*flags |= FLAGS_DID_CORE_STYLE;
}
switch (os_style) {
case OS_STYLE_NETBSD:
if (xnh_type == NT_NETBSD_CORE_PROCINFO) {
if (type == NT_NETBSD_CORE_PROCINFO) {
char sbuf[512];
uint32_t signo;
/*
* Extract the program name. It is at
@ -738,8 +686,9 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
* including the terminating NUL.
*/
if (file_printf(ms, ", from '%.31s'",
&nbuf[doff + 0x7c]) == -1)
return size;
file_printable(sbuf, sizeof(sbuf),
(const char *)&nbuf[doff + 0x7c])) == -1)
return 1;
/*
* Extract the signal number. It is at
@ -749,14 +698,14 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
sizeof(signo));
if (file_printf(ms, " (signal %u)",
elf_getu32(swap, signo)) == -1)
return size;
return 1;
*flags |= FLAGS_DID_CORE;
return size;
return 1;
}
break;
default:
if (xnh_type == NT_PRPSINFO && *flags & FLAGS_IS_CORE) {
if (type == NT_PRPSINFO && *flags & FLAGS_IS_CORE) {
size_t i, j;
unsigned char c;
/*
@ -824,7 +773,7 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
* Try next offsets, in case this match is
* in the middle of a string.
*/
for (k = i + 1 ; k < NOFFSETS ; k++) {
for (k = i + 1 ; k < NOFFSETS; k++) {
size_t no;
int adjust = 1;
if (prpsoffsets(k) >= prpsoffsets(i))
@ -849,9 +798,9 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
cp--;
if (file_printf(ms, ", from '%.*s'",
(int)(cp - cname), cname) == -1)
return size;
return 1;
*flags |= FLAGS_DID_CORE;
return size;
return 1;
tryanother:
;
@ -860,6 +809,129 @@ donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
break;
}
#endif
return 0;
}
private size_t
donote(struct magic_set *ms, void *vbuf, size_t offset, size_t size,
int clazz, int swap, size_t align, int *flags, uint16_t *notecount)
{
Elf32_Nhdr nh32;
Elf64_Nhdr nh64;
size_t noff, doff;
uint32_t namesz, descsz;
unsigned char *nbuf = CAST(unsigned char *, vbuf);
if (*notecount == 0)
return 0;
--*notecount;
if (xnh_sizeof + offset > size) {
/*
* We're out of note headers.
*/
return xnh_sizeof + offset;
}
(void)memcpy(xnh_addr, &nbuf[offset], xnh_sizeof);
offset += xnh_sizeof;
namesz = xnh_namesz;
descsz = xnh_descsz;
if ((namesz == 0) && (descsz == 0)) {
/*
* We're out of note headers.
*/
return (offset >= size) ? offset : size;
}
if (namesz & 0x80000000) {
(void)file_printf(ms, ", bad note name size 0x%lx",
(unsigned long)namesz);
return 0;
}
if (descsz & 0x80000000) {
(void)file_printf(ms, ", bad note description size 0x%lx",
(unsigned long)descsz);
return 0;
}
noff = offset;
doff = ELF_ALIGN(offset + namesz);
if (offset + namesz > size) {
/*
* We're past the end of the buffer.
*/
return doff;
}
offset = ELF_ALIGN(doff + descsz);
if (doff + descsz > size) {
/*
* We're past the end of the buffer.
*/
return (offset >= size) ? offset : size;
}
if ((*flags & FLAGS_DID_OS_NOTE) == 0) {
if (do_os_note(ms, nbuf, xnh_type, swap,
namesz, descsz, noff, doff, flags))
return size;
}
if ((*flags & FLAGS_DID_BUILD_ID) == 0) {
if (do_bid_note(ms, nbuf, xnh_type, swap,
namesz, descsz, noff, doff, flags))
return size;
}
if ((*flags & FLAGS_DID_NETBSD_PAX) == 0) {
if (do_pax_note(ms, nbuf, xnh_type, swap,
namesz, descsz, noff, doff, flags))
return size;
}
if ((*flags & FLAGS_DID_CORE) == 0) {
if (do_core_note(ms, nbuf, xnh_type, swap,
namesz, descsz, noff, doff, flags, size, clazz))
return size;
}
if (namesz == 7 && strcmp((char *)&nbuf[noff], "NetBSD") == 0) {
if (descsz > 100)
descsz = 100;
switch (xnh_type) {
case NT_NETBSD_VERSION:
return size;
case NT_NETBSD_MARCH:
if (*flags & FLAGS_DID_NETBSD_MARCH)
return size;
*flags |= FLAGS_DID_NETBSD_MARCH;
if (file_printf(ms, ", compiled for: %.*s",
(int)descsz, (const char *)&nbuf[doff]) == -1)
return size;
break;
case NT_NETBSD_CMODEL:
if (*flags & FLAGS_DID_NETBSD_CMODEL)
return size;
*flags |= FLAGS_DID_NETBSD_CMODEL;
if (file_printf(ms, ", compiler model: %.*s",
(int)descsz, (const char *)&nbuf[doff]) == -1)
return size;
break;
default:
if (*flags & FLAGS_DID_NETBSD_UNKNOWN)
return size;
*flags |= FLAGS_DID_NETBSD_UNKNOWN;
if (file_printf(ms, ", note=%u", xnh_type) == -1)
return size;
break;
}
return size;
}
return offset;
}
@ -915,7 +987,8 @@ static const cap_desc_t cap_desc_386[] = {
private int
doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
size_t size, off_t fsize, int *flags, int mach, int strtab)
size_t size, off_t fsize, int mach, int strtab, int *flags,
uint16_t *notecount)
{
Elf32_Shdr sh32;
Elf64_Shdr sh64;
@ -926,6 +999,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
uint64_t cap_hw1 = 0; /* SunOS 5.x hardware capabilites */
uint64_t cap_sf1 = 0; /* SunOS 5.x software capabilites */
char name[50];
ssize_t namesize;
if (size != xsh_sizeof) {
if (file_printf(ms, ", corrupted section header size") == -1)
@ -934,7 +1008,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
}
/* Read offset of name section to be able to read section names later */
if (pread(fd, xsh_addr, xsh_sizeof, off + size * strtab) == -1) {
if (pread(fd, xsh_addr, xsh_sizeof, off + size * strtab) < (ssize_t)xsh_sizeof) {
file_badread(ms);
return -1;
}
@ -942,15 +1016,15 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
for ( ; num; num--) {
/* Read the name of this section. */
if (pread(fd, name, sizeof(name), name_off + xsh_name) == -1) {
if ((namesize = pread(fd, name, sizeof(name) - 1, name_off + xsh_name)) == -1) {
file_badread(ms);
return -1;
}
name[sizeof(name) - 1] = '\0';
name[namesize] = '\0';
if (strcmp(name, ".debug_info") == 0)
stripped = 0;
if (pread(fd, xsh_addr, xsh_sizeof, off) == -1) {
if (pread(fd, xsh_addr, xsh_sizeof, off) < (ssize_t)xsh_sizeof) {
file_badread(ms);
return -1;
}
@ -980,7 +1054,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
" for note");
return -1;
}
if (pread(fd, nbuf, xsh_size, xsh_offset) == -1) {
if (pread(fd, nbuf, xsh_size, xsh_offset) < (ssize_t)xsh_size) {
file_badread(ms);
free(nbuf);
return -1;
@ -991,7 +1065,7 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
if (noff >= (off_t)xsh_size)
break;
noff = donote(ms, nbuf, (size_t)noff,
xsh_size, clazz, swap, 4, flags);
xsh_size, clazz, swap, 4, flags, notecount);
if (noff == 0)
break;
}
@ -1158,13 +1232,15 @@ doshn(struct magic_set *ms, int clazz, int swap, int fd, off_t off, int num,
*/
private int
dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
int num, size_t size, off_t fsize, int *flags, int sh_num)
int num, size_t size, off_t fsize, int sh_num, int *flags,
uint16_t *notecount)
{
Elf32_Phdr ph32;
Elf64_Phdr ph64;
const char *linking_style = "statically";
const char *shared_libraries = "";
const char *interp = "";
unsigned char nbuf[BUFSIZ];
char ibuf[BUFSIZ];
ssize_t bufsize;
size_t offset, align, len;
@ -1175,20 +1251,40 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
}
for ( ; num; num--) {
if (pread(fd, xph_addr, xph_sizeof, off) == -1) {
if (pread(fd, xph_addr, xph_sizeof, off) < (ssize_t)xph_sizeof) {
file_badread(ms);
return -1;
}
off += size;
bufsize = 0;
align = 4;
/* Things we can determine before we seek */
switch (xph_type) {
case PT_DYNAMIC:
linking_style = "dynamically";
break;
case PT_NOTE:
if (sh_num) /* Did this through section headers */
continue;
if (((align = xph_align) & 0x80000000UL) != 0 ||
align < 4) {
if (file_printf(ms,
", invalid note alignment 0x%lx",
(unsigned long)align) == -1)
return -1;
align = 4;
}
/*FALLTHROUGH*/
case PT_INTERP:
shared_libraries = " (uses shared libs)";
len = xph_filesz < sizeof(nbuf) ? xph_filesz
: sizeof(nbuf);
bufsize = pread(fd, nbuf, len, xph_offset);
if (bufsize == -1) {
file_badread(ms);
return -1;
}
break;
default:
if (fsize != SIZE_UNKNOWN && xph_offset > fsize) {
@ -1200,35 +1296,25 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
/* Things we can determine when we seek */
switch (xph_type) {
case PT_INTERP:
if (bufsize && nbuf[0]) {
nbuf[bufsize - 1] = '\0';
interp = (const char *)nbuf;
} else
interp = "*empty*";
break;
case PT_NOTE:
if (((align = xph_align) & 0x80000000UL) != 0 ||
align < 4) {
if (file_printf(ms,
", invalid note alignment 0x%lx",
(unsigned long)align) == -1)
return -1;
align = 4;
}
if (sh_num)
break;
/*
* This is a PT_NOTE section; loop through all the notes
* in the section.
*/
len = xph_filesz < sizeof(nbuf) ? xph_filesz
: sizeof(nbuf);
bufsize = pread(fd, nbuf, len, xph_offset);
if (bufsize == -1) {
file_badread(ms);
return -1;
}
offset = 0;
for (;;) {
if (offset >= (size_t)bufsize)
break;
offset = donote(ms, nbuf, offset,
(size_t)bufsize, clazz, swap, align,
flags);
flags, notecount);
if (offset == 0)
break;
}
@ -1237,9 +1323,13 @@ dophn_exec(struct magic_set *ms, int clazz, int swap, int fd, off_t off,
break;
}
}
if (file_printf(ms, ", %s linked%s", linking_style, shared_libraries)
if (file_printf(ms, ", %s linked", linking_style)
== -1)
return -1;
return -1;
if (interp[0])
if (file_printf(ms, ", interpreter %s",
file_printable(ibuf, sizeof(ibuf), interp)) == -1)
return -1;
return 0;
}
@ -1259,7 +1349,7 @@ file_tryelf(struct magic_set *ms, int fd, const unsigned char *buf,
int flags = 0;
Elf32_Ehdr elf32hdr;
Elf64_Ehdr elf64hdr;
uint16_t type, phnum, shnum;
uint16_t type, phnum, shnum, notecount;
if (ms->flags & (MAGIC_MIME|MAGIC_APPLE))
return 0;

View File

@ -32,7 +32,7 @@
#include "file.h"
#ifndef lint
FILE_RCSID("@(#)$File: softmagic.c,v 1.203 2014/12/04 15:22:05 christos Exp $")
FILE_RCSID("@(#)$File: softmagic.c,v 1.206 2015/01/01 17:07:34 christos Exp $")
#endif /* lint */
#include "magic.h"
@ -404,28 +404,6 @@ strndup(const char *str, size_t n)
}
#endif /* HAVE_STRNDUP */
static char *
printable(char *buf, size_t bufsiz, const char *str)
{
char *ptr, *eptr;
const unsigned char *s = (const unsigned char *)str;
for (ptr = buf, eptr = ptr + bufsiz - 1; ptr < eptr && *s; s++) {
if (isprint(*s)) {
*ptr++ = *s;
continue;
}
if (ptr >= eptr + 4)
break;
*ptr++ = '\\';
*ptr++ = ((*s >> 6) & 7) + '0';
*ptr++ = ((*s >> 3) & 7) + '0';
*ptr++ = ((*s >> 0) & 7) + '0';
}
*ptr = '\0';
return buf;
}
private int32_t
mprint(struct magic_set *ms, struct magic *m)
{
@ -433,7 +411,7 @@ mprint(struct magic_set *ms, struct magic *m)
float vf;
double vd;
int64_t t = 0;
char buf[128], tbuf[26];
char buf[128], tbuf[26], sbuf[512];
union VALUETYPE *p = &ms->ms_value;
switch (m->type) {
@ -527,12 +505,13 @@ mprint(struct magic_set *ms, struct magic *m)
case FILE_BESTRING16:
case FILE_LESTRING16:
if (m->reln == '=' || m->reln == '!') {
if (file_printf(ms, F(ms, m, "%s"), m->value.s) == -1)
if (file_printf(ms, F(ms, m, "%s"),
file_printable(sbuf, sizeof(sbuf), m->value.s))
== -1)
return -1;
t = ms->offset + m->vallen;
}
else {
char sbuf[512];
char *str = p->s;
/* compute t before we mangle the string? */
@ -555,7 +534,7 @@ mprint(struct magic_set *ms, struct magic *m)
}
if (file_printf(ms, F(ms, m, "%s"),
printable(sbuf, sizeof(sbuf), str)) == -1)
file_printable(sbuf, sizeof(sbuf), str)) == -1)
return -1;
if (m->type == FILE_PSTRING)
@ -659,7 +638,8 @@ mprint(struct magic_set *ms, struct magic *m)
file_oomem(ms, ms->search.rm_len);
return -1;
}
rval = file_printf(ms, F(ms, m, "%s"), cp);
rval = file_printf(ms, F(ms, m, "%s"),
file_printable(sbuf, sizeof(sbuf), cp));
free(cp);
if (rval == -1)
@ -673,7 +653,8 @@ mprint(struct magic_set *ms, struct magic *m)
}
case FILE_SEARCH:
if (file_printf(ms, F(ms, m, "%s"), m->value.s) == -1)
if (file_printf(ms, F(ms, m, "%s"),
file_printable(sbuf, sizeof(sbuf), m->value.s)) == -1)
return -1;
if ((m->str_flags & REGEX_OFFSET_START))
t = ms->search.offset;
@ -1684,6 +1665,8 @@ mget(struct magic_set *ms, const unsigned char *s, struct magic *m,
break;
case FILE_INDIRECT:
if (m->str_flags & INDIRECT_RELATIVE)
offset += o;
if (offset == 0)
return 0;

View File

@ -1,4 +1,4 @@
# Makefile.in generated by automake 1.14.1 from Makefile.am.
# Makefile.in generated by automake 1.14 from Makefile.am.
# @configure_input@
# Copyright (C) 1994-2013 Free Software Foundation, Inc.

View File

@ -262,7 +262,7 @@
#define PACKAGE_NAME "file"
/* Define to the full name and version of this package. */
#define PACKAGE_STRING "file 5.21"
#define PACKAGE_STRING "file 5.22"
/* Define to the one symbol short name of this package. */
#define PACKAGE_TARNAME "file"
@ -271,7 +271,7 @@
#define PACKAGE_URL ""
/* Define to the version of this package. */
#define PACKAGE_VERSION "5.21"
#define PACKAGE_VERSION "5.22"
/* Define to 1 if you have the ANSI C header files. */
#define STDC_HEADERS 1
@ -302,7 +302,7 @@
/* Version number of package */
#define VERSION "5.21"
#define VERSION "5.22"
/* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most
significant byte first (like Motorola and SPARC, unlike Intel). */