pdfalyzer 1.14.8__py3-none-any.whl → 1.14.10__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of pdfalyzer might be problematic. Click here for more details.

CHANGELOG.md CHANGED
@@ -1,5 +1,11 @@
1
1
  # NEXT RELEASE
2
2
 
3
+ ### 1.14.10
4
+ * Add `malware_MaldocinPDF` YARA rule
5
+
6
+ ### 1.14.9
7
+ * Add [ActiveMime YARA rule](https://blog.didierstevens.com/2023/08/29/quickpost-pdf-activemime-maldocs-yara-rule/)
8
+
3
9
  ### 1.14.8
4
10
  * Handle internal YARA errors more gracefully with error messages instead of crashes (currently seeing `ERROR_TOO_MANY_RE_FIBERS` on macOS on some files for unknown reasons that we hope will go away eventually)
5
11
 
@@ -30,7 +30,7 @@ from pdfalyzer.util.adobe_strings import CONTENTS, CURRENTFILE_EEXEC, FONT_FILE_
30
30
 
31
31
  class BinaryScanner:
32
32
  def __init__(self, _bytes: bytes, owner: PdfTreeNode, label: Optional[Text] = None):
33
- """owner is an optional link back to the object containing this binary"""
33
+ """'owner' arg is an optional link back to the object containing this binary."""
34
34
  self.bytes = _bytes
35
35
  self.label = label
36
36
  self.owner = owner
@@ -43,8 +43,8 @@ class BinaryScanner:
43
43
  self.regex_extraction_stats = defaultdict(lambda: RegexMatchMetrics())
44
44
 
45
45
  def check_for_dangerous_instructions(self) -> None:
46
- """Scan for all the strings in DANGEROUS_INSTRUCTIONS list and decode bytes around them"""
47
- subheader = "Scanning Binary For Anything That Could Be Described As 'Sus'..."
46
+ """Scan for all the strings in DANGEROUS_INSTRUCTIONS list and decode bytes around them."""
47
+ subheader = "Scanning Binary For Anything That Could Be Described As 'sus'..."
48
48
  print_section_sub_subheader(subheader, style=f"bright_red")
49
49
 
50
50
  for instruction in DANGEROUS_STRINGS:
@@ -62,7 +62,7 @@ class BinaryScanner:
62
62
  self.process_yara_matches(yaralyzer, instruction, force=True)
63
63
 
64
64
  def check_for_boms(self) -> None:
65
- """Check the binary data for BOMs"""
65
+ """Check the binary data for BOMs."""
66
66
  print_section_sub_subheader("Scanning Binary for any BOMs...", style='BOM')
67
67
 
68
68
  for bom_bytes, bom_name in BOMS.items():
@@ -105,11 +105,11 @@ class BinaryScanner:
105
105
  return self._quote_yaralyzer(QUOTE_PATTERNS[BACKTICK], BACKTICK).match_iterator()
106
106
 
107
107
  def extract_front_slash_quoted_bytes(self) -> Iterator[Tuple[BytesMatch, BytesDecoder]]:
108
- """Returns an interator over all strings surrounded by front_slashes (hint: regular expressions)"""
108
+ """Returns an interator over all strings surrounded by front_slashes (hint: regular expressions)."""
109
109
  return self._quote_yaralyzer(QUOTE_PATTERNS[FRONTSLASH], FRONTSLASH).match_iterator()
110
110
 
111
111
  def print_stream_preview(self, num_bytes=None, title_suffix=None) -> None:
112
- """Print a preview showing the beginning and end of the embedded stream data"""
112
+ """Print a preview showing the beginning and end of the embedded stream data."""
113
113
  num_bytes = num_bytes or PdfalyzerConfig._args.preview_stream_length or console_width()
114
114
  snipped_byte_count = self.stream_length - (num_bytes * 2)
115
115
  console.line()
@@ -134,7 +134,7 @@ class BinaryScanner:
134
134
  console.line()
135
135
 
136
136
  def process_yara_matches(self, yaralyzer: Yaralyzer, pattern: str, force: bool = False) -> None:
137
- """Decide whether to attempt to decode the matched bytes, track stats. force param ignores min/max length"""
137
+ """Decide whether to attempt to decode the matched bytes, track stats. force param ignores min/max length."""
138
138
  for bytes_match, decoder in yaralyzer.match_iterator():
139
139
  log.debug(f"Trackings stats for match: {pattern}, bytes_match: {bytes_match}, is_decodable: {bytes_match.is_decodable()}")
140
140
 
@@ -185,7 +185,7 @@ class BinaryScanner:
185
185
  )
186
186
 
187
187
  def _print_suppression_notices(self) -> None:
188
- """Print notices in queue in a single panel; empty queue"""
188
+ """Print the notices in queue in a single display panel and then empty the queue."""
189
189
  if len(self.suppression_notice_queue) == 0:
190
190
  return
191
191
 
@@ -195,5 +195,5 @@ class BinaryScanner:
195
195
  self.suppression_notice_queue = []
196
196
 
197
197
  def _eexec_idx(self) -> int:
198
- """Returns the location of CURRENTFILES_EEXEC within the binary stream dataor 0"""
198
+ """Returns the location of CURRENTFILES_EEXEC within the binary stream data (or 0 if it's not there)."""
199
199
  return self.bytes.find(CURRENTFILE_EEXEC) if CURRENTFILE_EEXEC in self.bytes else 0
@@ -1,5 +1,5 @@
1
1
  """
2
- Deprecated pre-tree, more rawformat reader.
2
+ Deprecated old, pre-tree, more rawformat reader.
3
3
  """
4
4
  from io import StringIO
5
5
 
@@ -47,7 +47,7 @@ class PdfObjectProperties:
47
47
  self.label = address
48
48
  self.type = root_address(address) if isinstance(address, str) else None
49
49
 
50
- # Force a string. TODO this sucks.
50
+ # Force self.label to be a string. TODO this sucks.
51
51
  if isinstance(self.label, int):
52
52
  self.label = f"{UNLABELED}[{self.label}]"
53
53
 
@@ -29,9 +29,9 @@ DECODE_FAILURE_LEN = -1
29
29
  class PdfTreeNode(NodeMixin, PdfObjectProperties):
30
30
  def __init__(self, obj: PdfObject, address: str, idnum: int):
31
31
  """
32
- obj: The underlying PDF object
33
- address: the first address that points from some node to this one
34
- idnum: ID used in the reference
32
+ obj: The underlying PDF object
33
+ address: The first address that points from some node to this one
34
+ idnum: ID used in the reference
35
35
  """
36
36
  PdfObjectProperties.__init__(self, obj, address, idnum)
37
37
  self.non_tree_relationships: List[PdfObjectRelationship] = []
@@ -54,7 +54,7 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
54
54
 
55
55
  @classmethod
56
56
  def from_reference(cls, ref: IndirectObject, address: str) -> 'PdfTreeNode':
57
- """Builds a PdfTreeDecorator from an IndirectObject"""
57
+ """Builds a PdfTreeDecorator from an IndirectObject."""
58
58
  try:
59
59
  return cls(ref.get_object(), address, ref.idnum)
60
60
  except PdfReadError as e:
@@ -90,7 +90,7 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
90
90
  log.info(f'Added other relationship: {relationship} {self}')
91
91
 
92
92
  def remove_non_tree_relationship(self, from_node: 'PdfTreeNode') -> None:
93
- """Remove all non_tree_relationships from from_node to this node"""
93
+ """Remove all non_tree_relationships from from_node to this node."""
94
94
  relationships_to_remove = [r for r in self.non_tree_relationships if r.from_node == from_node]
95
95
 
96
96
  if len(relationships_to_remove) == 0:
@@ -104,7 +104,7 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
104
104
  self.non_tree_relationships.remove(relationship)
105
105
 
106
106
  def nodes_with_here_references(self) -> List['PdfTreeNode']:
107
- """Return a list of nodes that contain this nodes PDF object as an IndirectObject reference"""
107
+ """Return a list of nodes that contain this nodes PDF object as an IndirectObject reference."""
108
108
  return [r.from_node for r in self.non_tree_relationships if r.from_node]
109
109
 
110
110
  def non_tree_relationship_count(self) -> int:
@@ -120,11 +120,11 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
120
120
  return list(addresses)
121
121
 
122
122
  def references_to_other_nodes(self) -> List[PdfObjectRelationship]:
123
- """Returns all nodes referenced from node.obj (see PdfObjectRelationship definition)"""
123
+ """Returns all nodes referenced from node.obj (see PdfObjectRelationship definition)."""
124
124
  return PdfObjectRelationship.build_node_references(from_node=self)
125
125
 
126
126
  def contains_stream(self) -> bool:
127
- """Returns True for ContentStream, DecodedStream, and EncodedStream objects"""
127
+ """Returns True for ContentStream, DecodedStream, and EncodedStream objects."""
128
128
  return isinstance(self.obj, StreamObject)
129
129
 
130
130
  def tree_address(self, max_length: Optional[int] = DEFAULT_MAX_ADDRESS_LENGTH) -> str:
@@ -144,7 +144,7 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
144
144
  return '...' + address[-max_length:][3:]
145
145
 
146
146
  def address_of_this_node_in_other(self, from_node: 'PdfTreeNode') -> Optional[str]:
147
- """Find the local address used in from_node to refer to this node"""
147
+ """Find the local address used in 'from_node' to refer to this node."""
148
148
  refs_to_this_node = [
149
149
  ref for ref in from_node.references_to_other_nodes()
150
150
  if ref.to_obj.idnum == self.idnum
@@ -189,7 +189,7 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
189
189
  SymlinkNode(self, parent=relationship.from_node)
190
190
 
191
191
  def descendants_count(self) -> int:
192
- """How many nodes in the tree are children/grandchildren/great grandchildren/etc of this one"""
192
+ """Count nodes in the tree that are children/grandchildren/great grandchildren/etc of this one."""
193
193
  return len(self.children) + sum([child.descendants_count() for child in self.children])
194
194
 
195
195
  def unique_labels_of_referring_nodes(self) -> List[str]:
@@ -211,7 +211,7 @@ class PdfTreeNode(NodeMixin, PdfObjectProperties):
211
211
  write_method(f" {i + 1}. {escape(str(r))}, Descendant Count: {r.from_node.descendants_count()}")
212
212
 
213
213
  def _colored_address(self, max_length: Optional[int] = None) -> Text:
214
- """Rich text version of tree_address()"""
214
+ """Rich text version of tree_address()."""
215
215
  text = Text('@', style='bright_white')
216
216
  return text.append(self.tree_address(max_length), style='address')
217
217
 
@@ -29,7 +29,7 @@ class PdfTreeVerifier:
29
29
  log.warning(msg)
30
30
 
31
31
  def verify_unencountered_are_untraversable(self) -> None:
32
- """Make sure any PDF object IDs we can't find in tree are /ObjStm or /Xref nodes"""
32
+ """Make sure any PDF object IDs we can't find in tree are /ObjStm or /Xref nodes."""
33
33
  if self.pdfalyzer.pdf_size is None:
34
34
  log.warning(f"{SIZE} not found in PDF trailer; cannot verify all nodes are in tree")
35
35
  return
@@ -1,5 +1,5 @@
1
1
  """
2
- Count the Javascript (at least the 3+ letter words, record big matches
2
+ Count the Javascript (at least the 3+ letter words, record big matches.
3
3
  """
4
4
  import re
5
5
 
@@ -1,5 +1,5 @@
1
1
  """
2
- Class to help with the pre-configured YARA rules in /yara.
2
+ Class to help with the pre-configured YARA rules in the /yara directory.
3
3
  """
4
4
  from importlib.resources import as_file, files
5
5
  from sys import exit
@@ -1,4 +1,6 @@
1
- """Some simple math helpers."""
1
+ """
2
+ Some simple math helpers.
3
+ """
2
4
 
3
5
 
4
6
  def is_divisible_by(n: int, divisor: int) -> bool:
@@ -6,7 +6,6 @@ from typing import List, Optional, Union
6
6
  from PyPDF2.generic import IndirectObject, PdfObject
7
7
  from yaralyzer.util.logging import log
8
8
 
9
- #from pdfalyzer.he import has_indeterminate_prefix
10
9
  from pdfalyzer.helpers.string_helper import bracketed, is_prefixed_by_any
11
10
  from pdfalyzer.util.adobe_strings import *
12
11
 
pdfalyzer/pdfalyzer.py CHANGED
@@ -13,8 +13,8 @@ from anytree import LevelOrderIter, SymlinkNode
13
13
  from anytree.search import findall, findall_by_attr
14
14
  from PyPDF2 import PdfReader
15
15
  from PyPDF2.generic import IndirectObject
16
- from yaralyzer.output.file_hashes_table import compute_file_hashes
17
16
  from yaralyzer.helpers.file_helper import load_binary_data
17
+ from yaralyzer.output.file_hashes_table import compute_file_hashes
18
18
  from yaralyzer.output.rich_console import console
19
19
  from yaralyzer.util.logging import log
20
20
 
@@ -983,3 +983,64 @@ rule PDF_JS_guillemet_close_in_Adobe_Type1_font
983
983
  $url_js_backtick_close_obj and Adobe_Type_1_Font
984
984
  }
985
985
 
986
+
987
+ rule rule_pdf_activemime {
988
+ meta:
989
+ author = "Didier Stevens"
990
+ date = "2023/08/29"
991
+ version = "0.0.1"
992
+ samples = "5b677d297fb862c2d223973697479ee53a91d03073b14556f421b3d74f136b9d,098796e1b82c199ad226bff056b6310262b132f6d06930d3c254c57bdf548187,ef59d7038cfd565fd65bae12588810d5361df938244ebad33b71882dcf683058"
993
+ description = "look for files that start with %PDF- and contain BASE64 encoded string ActiveMim (QWN0aXZlTWlt), possibly obfuscated with extra whitespace characters"
994
+ usage = "if you don't have to care about YARA performance warnings, you can uncomment string $base64_ActiveMim0 and remove all other $base64_ActiveMim## strings"
995
+ strings:
996
+ $pdf = "%PDF-"
997
+ // $base64_ActiveMim0 = /[ \t\r\n]*Q[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
998
+ $base64_ActiveMim1 = /Q [ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
999
+ $base64_ActiveMim2 = /Q \t[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1000
+ $base64_ActiveMim3 = /Q \r[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1001
+ $base64_ActiveMim4 = /Q \n[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1002
+ $base64_ActiveMim5 = /Q\t [ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1003
+ $base64_ActiveMim6 = /Q\t\t[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1004
+ $base64_ActiveMim7 = /Q\t\r[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1005
+ $base64_ActiveMim8 = /Q\t\n[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1006
+ $base64_ActiveMim9 = /Q\r [ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1007
+ $base64_ActiveMim10 = /Q\r\t[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1008
+ $base64_ActiveMim11 = /Q\r\r[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1009
+ $base64_ActiveMim12 = /Q\r\n[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1010
+ $base64_ActiveMim13 = /Q\n [ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1011
+ $base64_ActiveMim14 = /Q\n\t[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1012
+ $base64_ActiveMim15 = /Q\n\r[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1013
+ $base64_ActiveMim16 = /Q\n\n[ \t\r\n]*W[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1014
+ $base64_ActiveMim17 = /QW [ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1015
+ $base64_ActiveMim18 = /QW\t[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1016
+ $base64_ActiveMim19 = /QW\r[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1017
+ $base64_ActiveMim20 = /QW\n[ \t\r\n]*N[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1018
+ $base64_ActiveMim21 = /QWN[ \t\r\n]*0[ \t\r\n]*a[ \t\r\n]*X[ \t\r\n]*Z[ \t\r\n]*l[ \t\r\n]*T[ \t\r\n]*W[ \t\r\n]*l[ \t\r\n]*t/
1019
+ condition:
1020
+ $pdf at 0 and any of ($base64_ActiveMim*)
1021
+ }
1022
+
1023
+
1024
+ rule malware_MaldocinPDF {
1025
+ meta:
1026
+ author = "Yuma Masubuchi and Kota Kino"
1027
+ description = "Search for embeddings of malicious Word files into a PDF file."
1028
+ created_date = "2023-08-15"
1029
+ blog_reference = "https://malware.news/t/maldoc-in-pdf-detection-bypass-by-embedding-a-malicious-word-file-into-a-pdf-file/72815"
1030
+ labs_reference = "N/A"
1031
+ labs_pivot = "N/A"
1032
+ samples = "ef59d7038cfd565fd65bae12588810d5361df938244ebad33b71882dcf683058"
1033
+
1034
+ strings:
1035
+ $docfile2 = "<w:WordDocument>" ascii nocase
1036
+ $xlsfile2 = "<x:ExcelWorkbook>" ascii nocase
1037
+ $mhtfile0 = "mime" ascii nocase
1038
+ $mhtfile1 = "content-location:" ascii nocase
1039
+ $mhtfile2 = "content-type:" ascii nocase
1040
+
1041
+ condition:
1042
+ (uint32(0) == 0x46445025) and
1043
+ (1 of ($mhtfile*)) and
1044
+ ( (1 of ($docfile*)) or
1045
+ (1 of ($xlsfile*)) )
1046
+ }
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: pdfalyzer
3
- Version: 1.14.8
3
+ Version: 1.14.10
4
4
  Summary: A PDF analysis toolkit. Scan a PDF with relevant YARA rules, visualize its inner tree-like data structure in living color (lots of colors), force decodes of suspicious font binaries, and more.
5
5
  Home-page: https://github.com/michelcrypt4d4mus/pdfalyzer
6
6
  License: GPL-3.0-or-later
@@ -1,21 +1,21 @@
1
- CHANGELOG.md,sha256=2_xgeLXSP3688zMVp7Tfa2BCoh9XzuKQV9L85gFgZ1c,11016
1
+ CHANGELOG.md,sha256=9AcJopi6RSNZErSW00CtbeXPLf0fz4GGgchYWzctL9E,11195
2
2
  LICENSE,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
3
3
  pdfalyzer/__init__.py,sha256=bip0vBCQXxNVwZrQdT15_YVqE5o7IfS4HZnE38rnqzA,3188
4
4
  pdfalyzer/__main__.py,sha256=Ko_AoAyYMLIe_cmhiUSl6twheLZrGyT8aOSJ2CP7EZY,43
5
- pdfalyzer/binary/binary_scanner.py,sha256=iZN0vrqBFgADR3ACGY5SE9wAcQcNs0hlGgrMg1530sg,10121
5
+ pdfalyzer/binary/binary_scanner.py,sha256=Vl1BarQdk99jDl_NZkBhK85u3auRZrjeR37rThwnzzk,10180
6
6
  pdfalyzer/config.py,sha256=oN-pVR037lt3giRsnsm4c8ku5hCW8ChFqYFi9V7w1qU,1918
7
- pdfalyzer/decorators/document_model_printer.py,sha256=lp6PvyVsxfNzW9k2IEe_8zmAtrPLiGdeFv3F5fCBfpg,2642
7
+ pdfalyzer/decorators/document_model_printer.py,sha256=1fGvbCnMBzpwgePxCIMj1nWUN1lpVtJ1sApTa2sJ3yU,2647
8
8
  pdfalyzer/decorators/indeterminate_node.py,sha256=f9Us3Vpr7DIA7PUEvLoMSurRyWySFTiT6Pyjt120PRs,6449
9
- pdfalyzer/decorators/pdf_object_properties.py,sha256=28jNnav9NYVfMphF7HZQpau0NLV9m-Fzg-S2jBZrkUU,5507
10
- pdfalyzer/decorators/pdf_tree_node.py,sha256=kdMXdlfcGhaHFDvHjVxFL4jFQ8NJvNXFm53KddxKG7Q,10737
11
- pdfalyzer/decorators/pdf_tree_verifier.py,sha256=pk0NysYt8PxsKh532IfNSrcoHpdb-wUxUw2TjJFVqDM,4542
9
+ pdfalyzer/decorators/pdf_object_properties.py,sha256=8dqHmi0J2USwnGPSy0Sg_ria_2TsaRWe_HWs-14RKrg,5524
10
+ pdfalyzer/decorators/pdf_tree_node.py,sha256=nIkur38BijcRD-bTJJPrSP25LR9Oiew2E3flzsEZHoQ,10755
11
+ pdfalyzer/decorators/pdf_tree_verifier.py,sha256=IRgm7ikdaqJEq66q3JcMZo49XQoONODM7lySioJfxRc,4543
12
12
  pdfalyzer/detection/constants/binary_regexes.py,sha256=rcgQ984q6a8CFvV2QX4-asuqT5w_aH8LPqoN2N13eOM,1665
13
13
  pdfalyzer/detection/constants/javascript_reserved_keywords.py,sha256=CXXdWskdQa0Hs5wCci2RBVvipgZg34_cLfmkWG4Xcmg,991
14
- pdfalyzer/detection/javascript_hunter.py,sha256=pxdy_NIr15uRLvus-iDGpFFCPokf_mSqQJUPndYsD64,710
15
- pdfalyzer/detection/yaralyzer_helper.py,sha256=v0XN36F2EjioAi4rP1qNqEj_aZJOMDfVQhGiY3Xg66I,1750
14
+ pdfalyzer/detection/javascript_hunter.py,sha256=_wT2vkKTMlm_RGCjYsmwcmV-ag1qep3EpkHmUw0nWcQ,711
15
+ pdfalyzer/detection/yaralyzer_helper.py,sha256=hmrnvTVtaX9l4FbXQrtrdXYHaK_IFSTDIuEWBIDPN74,1764
16
16
  pdfalyzer/font_info.py,sha256=L5ykKvlifAQv2uw-pKqxbQPqWrvbli0IcO8DgDK0SQo,6665
17
17
  pdfalyzer/helpers/dict_helper.py,sha256=2TP0_EJBouaWD6jfnAekrEZ4M5eHKL8Tm61FgXZtBAg,303
18
- pdfalyzer/helpers/number_helper.py,sha256=9XVxI6fygHIb0oqkOmFQUlvTxED9QKtwxvIYYGyUYU8,290
18
+ pdfalyzer/helpers/number_helper.py,sha256=8IlRmaOVLJsUV18VLvWRZU8SzRxL0XZjrY3sjmk2Ro4,292
19
19
  pdfalyzer/helpers/pdf_object_helper.py,sha256=u0j8B9mY8s5cTGo5LmDcozotvvgZNrwwJ4w_ipQqiXw,1105
20
20
  pdfalyzer/helpers/rich_text_helper.py,sha256=Ytd1n1ONmEe7BxEwT-LLT6rt7QF-m_wnapPdwWYT4Pc,1800
21
21
  pdfalyzer/helpers/string_helper.py,sha256=75EDEFw3UWHvWF32WtvZVBbqYY3ozO4y30dtH2qVMX0,2278
@@ -28,19 +28,19 @@ pdfalyzer/output/tables/decoding_stats_table.py,sha256=mhQOiWhmovaC4sop38WcxStv_
28
28
  pdfalyzer/output/tables/font_summary_table.py,sha256=xfTqC7BlQd0agQf6nDDhkcJno7hru6mf9_xY1f5IDcw,2065
29
29
  pdfalyzer/output/tables/pdf_node_rich_table.py,sha256=Soz5gkSl9pMFbwmGxyKyil_9X-Pl-fI0i8s0cvwLC3Q,5909
30
30
  pdfalyzer/output/tables/stream_objects_table.py,sha256=nzCTci8Kqs8Pyghad3L5KWHDdIWRSrKCRNW8geA_rMo,707
31
- pdfalyzer/pdf_object_relationship.py,sha256=fQs0Jx1Tx2aC-ON_hGBMJ96vWkL7JOP_ykustQWVzDQ,5391
32
- pdfalyzer/pdfalyzer.py,sha256=hifxJfBPoAWL8EJPQ7nEnI5WvijFj3ijlFJ2D4zkp3E,11016
31
+ pdfalyzer/pdf_object_relationship.py,sha256=EgeIiVDofvZd-il114H8ZlKKwCOci5T5S4e15mHK_Wg,5340
32
+ pdfalyzer/pdfalyzer.py,sha256=sOZqOKiRivd2I0Lek_cbYu0h4jIi8DXYnw5H0f6TfcA,11016
33
33
  pdfalyzer/util/adobe_strings.py,sha256=A4V3BI2pOaOmF4_RCbtsLxfv5LBWWKVtqrW562DzR6Y,4983
34
34
  pdfalyzer/util/argument_parser.py,sha256=EiOBaMRFvb9C_Zq3Odhw0KECSvElEfm8hGyljsOmzV4,8053
35
35
  pdfalyzer/util/debugging.py,sha256=nE64VUQbdu2OQRC8w8-AJkMtBOy8Kf3mjozuFslfWsw,156
36
36
  pdfalyzer/util/exceptions.py,sha256=XLFFTdx1n6i_VCmvuzvIOCa-djJvGEitfo9lhy3zq0k,98
37
37
  pdfalyzer/util/pdf_parser_manager.py,sha256=FVRYAYsCd0y5MAm--qvXnwCZnDtB3x85FdJtb-gpyw4,3109
38
- pdfalyzer/yara_rules/PDF.yara,sha256=sEUx5t0knhHcUJgHciN3TdZ2Bfp4OnvmrCLlmhFCICo,33476
38
+ pdfalyzer/yara_rules/PDF.yara,sha256=uTBPFzbNb91eWnAM_LzXMKodBxAz2Rj804kQDyeARc8,38667
39
39
  pdfalyzer/yara_rules/PDF_binary_stream.yara,sha256=oWRPLe5yQiRFMvi3BTHNTlB6T7NcAuxKn0C9OSvgJSM,804
40
40
  pdfalyzer/yara_rules/__init.py__,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
41
41
  pdfalyzer/yara_rules/lprat.static_file_analysis.yara,sha256=i0CwRH8pBx_QshKFTQtr1CP5n378EZelsF2FxMY2y5A,21859
42
- pdfalyzer-1.14.8.dist-info/LICENSE,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
43
- pdfalyzer-1.14.8.dist-info/METADATA,sha256=YttrTxzkQ-qUG-7cBTEgELT8B4wWAisaTxU17FAo63Q,24474
44
- pdfalyzer-1.14.8.dist-info/WHEEL,sha256=d2fvjOD7sXsVzChCqf0Ty0JbHKBaLYwDbGQDwQTnJ50,88
45
- pdfalyzer-1.14.8.dist-info/entry_points.txt,sha256=rl7OpBvxSNmV90rjTPCjhXTtjRMqZxHUAQfP0Cdmt1Y,111
46
- pdfalyzer-1.14.8.dist-info/RECORD,,
42
+ pdfalyzer-1.14.10.dist-info/LICENSE,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
43
+ pdfalyzer-1.14.10.dist-info/METADATA,sha256=7HuP-rQptGKP3S_BfTMDjHtetCU663pfNYJH7j4B1yw,24475
44
+ pdfalyzer-1.14.10.dist-info/WHEEL,sha256=d2fvjOD7sXsVzChCqf0Ty0JbHKBaLYwDbGQDwQTnJ50,88
45
+ pdfalyzer-1.14.10.dist-info/entry_points.txt,sha256=rl7OpBvxSNmV90rjTPCjhXTtjRMqZxHUAQfP0Cdmt1Y,111
46
+ pdfalyzer-1.14.10.dist-info/RECORD,,