docs: def extract_features_using_pefile(self, pef):
          ''' Process the PE File using the Python pefile module. '''
  
          # Store all extracted features into feature lists
          extracted_dense = {}
          extracted_sparse = {}
  
          # Now slog through the info and extract the features
          feature_not_found_flag = -99
          feature_default_value = 0
          self._warnings = []
  
          # Set all the dense features and sparse features to 'feature not found'
          # value and then check later to see if it was found
          for feature in self._dense_feature_list:
              extracted_dense[feature] = feature_not_found_flag
          for feature in self._sparse_feature_list:
              extracted_sparse[feature] = feature_not_found_flag
  
          # Check to make sure all the section names are standard
          std_sections = ['.text', '.bss', '.rdata', '.data', '.rsrc', '.edata', '.idata',
                          '.pdata', '.debug', '.reloc', '.stab', '.stabstr', '.tls',
                          '.crt', '.gnu_deb', '.eh_fram', '.exptbl', '.rodata']
          for i in range(200):
              std_sections.append('/'+str(i))
          std_section_names = 1
          extracted_sparse['section_names'] = []
          for section in pef.sections:
              name = convert_to_ascii_null_term(section.Name).lower()
              extracted_sparse['section_names'].append(name)
              if name not in std_sections:
                  std_section_names = 0
  
          extracted_dense['std_section_names'] = std_section_names
          extracted_dense['debug_size'] = pef.OPTIONAL_HEADER.DATA_DIRECTORY[6].Size
          extracted_dense['major_version'] = pef.OPTIONAL_HEADER.MajorImageVersion
          extracted_dense['minor_version'] = pef.OPTIONAL_HEADER.MinorImageVersion
          extracted_dense['iat_rva']	 = pef.OPTIONAL_HEADER.DATA_DIRECTORY[1].VirtualAddress
          extracted_dense['export_size'] = pef.OPTIONAL_HEADER.DATA_DIRECTORY[0].Size
          extracted_dense['check_sum'] = pef.OPTIONAL_HEADER.CheckSum
          try:
              extracted_dense['generated_check_sum'] = pef.generate_checksum()
          except ValueError:
              extracted_dense['generated_check_sum'] = 0
          if len(pef.sections) > 0:
              extracted_dense['virtual_address'] = pef.sections[0].VirtualAddress
              extracted_dense['virtual_size'] = pef.sections[0].Misc_VirtualSize
          extracted_dense['number_of_sections'] = pef.FILE_HEADER.NumberOfSections
          extracted_dense['compile_date'] = pef.FILE_HEADER.TimeDateStamp
          extracted_dense['number_of_rva_and_sizes'] = pef.OPTIONAL_HEADER.NumberOfRvaAndSizes
          extracted_dense['total_size_pe'] = len(pef.__data__)
  
          # Number of import and exports
          if hasattr(pef, 'DIRECTORY_ENTRY_IMPORT'):
              extracted_dense['number_of_imports'] = len(pef.DIRECTORY_ENTRY_IMPORT)
              num_imported_symbols = 0
              for module in pef.DIRECTORY_ENTRY_IMPORT:
                  num_imported_symbols += len(module.imports)
              extracted_dense['number_of_import_symbols'] = num_imported_symbols
  
          if hasattr(pef, 'DIRECTORY_ENTRY_BOUND_IMPORT'):
              extracted_dense['number_of_bound_imports'] = len(pef.DIRECTORY_ENTRY_BOUND_IMPORT)
              num_imported_symbols = 0
              for module in pef.DIRECTORY_ENTRY_BOUND_IMPORT:
                  num_imported_symbols += len(module.entries)
              extracted_dense['number_of_bound_import_symbols'] = num_imported_symbols
  
          if hasattr(pef, 'DIRECTORY_ENTRY_EXPORT'):
              try:
                  extracted_dense['number_of_export_symbols'] = len(pef.DIRECTORY_ENTRY_EXPORT.symbols)
                  symbol_set = set()
                  for symbol in pef.DIRECTORY_ENTRY_EXPORT.symbols:
                      symbol_info = 'unknown'
                      if not symbol.name:
                          symbol_info = 'ordinal=' + str(symbol.ordinal)
                      else:
                          symbol_info = 'name=' + symbol.name
                      symbol_set.add(convert_to_utf8('%s' % (symbol_info)).lower())
  
                  # Now convert set to list and add to features
                  extracted_sparse['ExportedSymbols'] = list(symbol_set)
  
              except AttributeError:
                  extracted_sparse['ExportedSymbols'] = ['AttributeError']
  
          # Specific Import info (Note this will be a sparse field woo hoo!)
          if hasattr(pef, 'DIRECTORY_ENTRY_IMPORT'):
              symbol_set = set()
              for module in pef.DIRECTORY_ENTRY_IMPORT:
                  for symbol in module.imports:
                      symbol_info = 'unknown'
                      if symbol.import_by_ordinal is True:
                          symbol_info = 'ordinal=' + str(symbol.ordinal)
                      else:
                          symbol_info = 'name=' + symbol.name
                          # symbol_info['hint'] = symbol.hint
                      if symbol.bound:
                          symbol_info += ' bound=' + str(symbol.bound)
  
                      symbol_set.add(convert_to_utf8('%s:%s' % (module.dll, symbol_info)).lower())
  
              # Now convert set to list and add to features
              extracted_sparse['imported_symbols'] = list(symbol_set)
  
          # Do we have a second section
          if len(pef.sections) >= 2:
              extracted_dense['virtual_size_2'] = pef.sections[1].Misc_VirtualSize
  
          extracted_dense['size_image'] = pef.OPTIONAL_HEADER.SizeOfImage
          extracted_dense['size_code'] = pef.OPTIONAL_HEADER.SizeOfCode
          extracted_dense['size_initdata'] = pef.OPTIONAL_HEADER.SizeOfInitializedData
          extracted_dense['size_uninit'] = pef.OPTIONAL_HEADER.SizeOfUninitializedData
          extracted_dense['pe_majorlink'] = pef.OPTIONAL_HEADER.MajorLinkerVersion
          extracted_dense['pe_minorlink'] = pef.OPTIONAL_HEADER.MinorLinkerVersion
          extracted_dense['pe_driver'] = 1 if pef.is_driver() else 0
          extracted_dense['pe_exe'] = 1 if pef.is_exe() else 0
          extracted_dense['pe_dll'] = 1 if pef.is_dll() else 0
          extracted_dense['pe_i386'] = 1
          if pef.FILE_HEADER.Machine != 0x014c:
              extracted_dense['pe_i386'] = 0
          extracted_dense['pe_char'] = pef.FILE_HEADER.Characteristics
  
          # Data directory features!!
          datadirs = { 
              0: 'IMAGE_DIRECTORY_ENTRY_EXPORT', 1: 'IMAGE_DIRECTORY_ENTRY_IMPORT', 
              2: 'IMAGE_DIRECTORY_ENTRY_RESOURCE', 5: 'IMAGE_DIRECTORY_ENTRY_BASERELOC', 
              12: 'IMAGE_DIRECTORY_ENTRY_IAT'}
          for idx, datadir in datadirs.items():
              datadir = pefile.DIRECTORY_ENTRY[idx]
              if len(pef.OPTIONAL_HEADER.DATA_DIRECTORY) <= idx:
                  continue
  
              directory = pef.OPTIONAL_HEADER.DATA_DIRECTORY[idx]
              extracted_dense['datadir_%s_size' % datadir] = directory.Size
  
          # Section features
          section_flags = ['IMAGE_SCN_MEM_EXECUTE', 'IMAGE_SCN_CNT_CODE', 'IMAGE_SCN_MEM_WRITE', 'IMAGE_SCN_MEM_READ']
          rawexecsize = 0
          vaexecsize = 0
          for sec in pef.sections:
              if not sec:
                  continue
  
              for char in section_flags:
                  # does the section have one of our attribs?
                  if hasattr(sec, char):
                      rawexecsize += sec.SizeOfRawData
                      vaexecsize += sec.Misc_VirtualSize
                      break
  
              # Take out any weird characters in section names
              secname = convert_to_ascii_null_term(sec.Name).lower()
              secname = secname.replace('.', '')
              if secname in std_sections:
                  extracted_dense['sec_entropy_%s' % secname] = sec.get_entropy()
                  extracted_dense['sec_rawptr_%s' % secname] = sec.PointerToRawData
                  extracted_dense['sec_rawsize_%s' % secname] = sec.SizeOfRawData
                  extracted_dense['sec_vasize_%s' % secname] = sec.Misc_VirtualSize
  
          extracted_dense['sec_va_execsize'] = vaexecsize
          extracted_dense['sec_raw_execsize'] = rawexecsize
  
          # Imphash (implemented in pefile 1.2.10-139 or later)
          try:
              extracted_sparse['imp_hash'] = pef.get_imphash()
          except AttributeError:
              extracted_sparse['imp_hash'] = 'Not found: Install pefile 1.2.10-139 or later'
  
          # Register if there were any pe warnings
          warnings = pef.get_warnings()
          if warnings:
              extracted_dense['pe_warnings'] = 1
              extracted_sparse['pe_warning_strings'] = warnings
          else:
              extracted_dense['pe_warnings'] = 0
  
          # Issue a warning if the feature isn't found
          for feature in self._dense_feature_list:
              if extracted_dense[feature] == feature_not_found_flag:
                  extracted_dense[feature] = feature_default_value
                  if (self._verbose):
                      print 'info: Feature: %s not found! Setting to %d' % (feature, feature_default_value)
  
          # Issue a warning if the feature isn't found
          for feature in self._sparse_feature_list:
              if extracted_sparse[feature] == feature_not_found_flag:
                  extracted_sparse[feature] = []  # For sparse data probably best default
                  if (self._verbose):
                      print 'info: Feature: %s not found! Setting to %d' % (feature, feature_default_value)
  
          # Set the features for the class var
          self._dense_features = extracted_dense
          self._sparse_features = extracted_sparse
  
          return self.get_dense_features(), self.get_sparse_features()