fastcrypter 2.3.0__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.
- fastcrypter/__init__.py +285 -0
- fastcrypter/advanced_encryptor.py +368 -0
- fastcrypter/algorithms/__init__.py +119 -0
- fastcrypter/algorithms/compression/__init__.py +17 -0
- fastcrypter/algorithms/encryption/__init__.py +17 -0
- fastcrypter/core/__init__.py +16 -0
- fastcrypter/core/compressor.py +409 -0
- fastcrypter/core/custom_encoder.py +309 -0
- fastcrypter/core/encryptor.py +703 -0
- fastcrypter/core/enhanced_compressor.py +542 -0
- fastcrypter/core/key_manager.py +315 -0
- fastcrypter/exceptions.py +219 -0
- fastcrypter/file_encryptor.py +135 -0
- fastcrypter/secure_compressor.py +568 -0
- fastcrypter/utils/__init__.py +17 -0
- fastcrypter-2.3.0.dist-info/METADATA +381 -0
- fastcrypter-2.3.0.dist-info/RECORD +21 -0
- fastcrypter-2.3.0.dist-info/WHEEL +5 -0
- fastcrypter-2.3.0.dist-info/entry_points.txt +2 -0
- fastcrypter-2.3.0.dist-info/licenses/LICENSE +21 -0
- fastcrypter-2.3.0.dist-info/top_level.txt +1 -0
|
@@ -0,0 +1,542 @@
|
|
|
1
|
+
"""
|
|
2
|
+
Enhanced Compressor with Native Library Integration
|
|
3
|
+
|
|
4
|
+
This module provides an enhanced version of the compressor that automatically
|
|
5
|
+
uses native C/C++ libraries when available for maximum performance.
|
|
6
|
+
"""
|
|
7
|
+
|
|
8
|
+
from typing import Union, Optional, Dict, Any
|
|
9
|
+
from .compressor import Compressor, CompressionAlgorithmType, CompressionLevel
|
|
10
|
+
from .encryptor import Encryptor, EncryptionAlgorithmType
|
|
11
|
+
from .key_manager import KeyManager
|
|
12
|
+
from .custom_encoder import CustomEncoder
|
|
13
|
+
from ..exceptions import EncrypterError, ValidationError, ErrorCodes
|
|
14
|
+
|
|
15
|
+
# Import native library support
|
|
16
|
+
try:
|
|
17
|
+
from ..native.native_loader import (
|
|
18
|
+
get_native_manager, get_crypto_core, get_hash_algorithms, is_native_available
|
|
19
|
+
)
|
|
20
|
+
NATIVE_SUPPORT = True
|
|
21
|
+
except ImportError:
|
|
22
|
+
NATIVE_SUPPORT = False
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
class EnhancedCompressor:
|
|
26
|
+
"""
|
|
27
|
+
Enhanced compressor with native library integration for maximum performance.
|
|
28
|
+
|
|
29
|
+
This class automatically detects and uses native C/C++ libraries when available,
|
|
30
|
+
falling back to pure Python implementations when necessary.
|
|
31
|
+
"""
|
|
32
|
+
|
|
33
|
+
def __init__(self,
|
|
34
|
+
password: str,
|
|
35
|
+
compression_algorithm: Union[CompressionAlgorithmType, str] = CompressionAlgorithmType.ZLIB,
|
|
36
|
+
compression_level: Union[CompressionLevel, int] = CompressionLevel.BALANCED,
|
|
37
|
+
encryption_algorithm: Union[EncryptionAlgorithmType, str] = EncryptionAlgorithmType.AES_256_GCM,
|
|
38
|
+
auto_select_compression: bool = True,
|
|
39
|
+
kdf_algorithm: str = 'pbkdf2',
|
|
40
|
+
kdf_iterations: int = 100000,
|
|
41
|
+
custom_charset: Optional[str] = None,
|
|
42
|
+
prefer_native: bool = True):
|
|
43
|
+
"""
|
|
44
|
+
Initialize the EnhancedCompressor.
|
|
45
|
+
|
|
46
|
+
Args:
|
|
47
|
+
password (str): Password for encryption key derivation.
|
|
48
|
+
compression_algorithm: Compression algorithm to use.
|
|
49
|
+
compression_level: Compression level (1-9).
|
|
50
|
+
encryption_algorithm: Encryption algorithm to use.
|
|
51
|
+
auto_select_compression (bool): Auto-select best compression algorithm.
|
|
52
|
+
kdf_algorithm (str): Key derivation function algorithm.
|
|
53
|
+
kdf_iterations (int): Number of KDF iterations.
|
|
54
|
+
custom_charset (str, optional): Custom character set for encoding output.
|
|
55
|
+
prefer_native (bool): Prefer native libraries when available.
|
|
56
|
+
"""
|
|
57
|
+
# Validate password
|
|
58
|
+
if not password or len(password) < 8:
|
|
59
|
+
raise ValidationError(
|
|
60
|
+
"Password must be at least 8 characters long",
|
|
61
|
+
ErrorCodes.KEY_TOO_WEAK
|
|
62
|
+
)
|
|
63
|
+
|
|
64
|
+
self.password = password
|
|
65
|
+
self.prefer_native = prefer_native and NATIVE_SUPPORT
|
|
66
|
+
|
|
67
|
+
# Initialize native library manager
|
|
68
|
+
if self.prefer_native:
|
|
69
|
+
self.native_manager = get_native_manager()
|
|
70
|
+
self.crypto_core = get_crypto_core()
|
|
71
|
+
self.hash_algorithms = get_hash_algorithms()
|
|
72
|
+
else:
|
|
73
|
+
self.native_manager = None
|
|
74
|
+
self.crypto_core = None
|
|
75
|
+
self.hash_algorithms = None
|
|
76
|
+
|
|
77
|
+
# Initialize standard components
|
|
78
|
+
self.compressor = Compressor(
|
|
79
|
+
algorithm=compression_algorithm,
|
|
80
|
+
level=compression_level,
|
|
81
|
+
auto_select=auto_select_compression
|
|
82
|
+
)
|
|
83
|
+
|
|
84
|
+
self.encryptor = Encryptor(
|
|
85
|
+
algorithm=encryption_algorithm,
|
|
86
|
+
derive_key=True
|
|
87
|
+
)
|
|
88
|
+
|
|
89
|
+
self.key_manager = KeyManager(
|
|
90
|
+
kdf_algorithm=kdf_algorithm,
|
|
91
|
+
iterations=kdf_iterations
|
|
92
|
+
)
|
|
93
|
+
|
|
94
|
+
# Initialize custom encoder if charset provided
|
|
95
|
+
self.custom_encoder = None
|
|
96
|
+
if custom_charset:
|
|
97
|
+
self.custom_encoder = CustomEncoder(charset=custom_charset)
|
|
98
|
+
|
|
99
|
+
# Store configuration
|
|
100
|
+
self.config = {
|
|
101
|
+
'compression_algorithm': compression_algorithm,
|
|
102
|
+
'compression_level': compression_level,
|
|
103
|
+
'encryption_algorithm': encryption_algorithm,
|
|
104
|
+
'auto_select_compression': auto_select_compression,
|
|
105
|
+
'kdf_algorithm': kdf_algorithm,
|
|
106
|
+
'kdf_iterations': kdf_iterations,
|
|
107
|
+
'custom_charset': custom_charset,
|
|
108
|
+
'prefer_native': self.prefer_native,
|
|
109
|
+
'native_available': self.is_native_available(),
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
def is_native_available(self) -> bool:
|
|
113
|
+
"""Check if native libraries are available."""
|
|
114
|
+
return self.prefer_native and (self.crypto_core is not None or self.hash_algorithms is not None)
|
|
115
|
+
|
|
116
|
+
def _fast_key_derivation(self, password: str, salt: bytes, iterations: int, key_length: int) -> bytes:
|
|
117
|
+
"""Use native key derivation if available."""
|
|
118
|
+
if self.hash_algorithms:
|
|
119
|
+
try:
|
|
120
|
+
password_bytes = password.encode('utf-8')
|
|
121
|
+
return self.hash_algorithms.fast_pbkdf2(password_bytes, salt, iterations, key_length)
|
|
122
|
+
except Exception:
|
|
123
|
+
pass
|
|
124
|
+
|
|
125
|
+
# Fallback to standard key manager
|
|
126
|
+
return self.key_manager.derive_key(password, salt, key_length)
|
|
127
|
+
|
|
128
|
+
def _fast_compression(self, data: bytes) -> bytes:
|
|
129
|
+
"""Use native compression if available."""
|
|
130
|
+
if self.crypto_core:
|
|
131
|
+
try:
|
|
132
|
+
# Try native RLE compression first
|
|
133
|
+
compressed = self.crypto_core.fast_compress_rle(data)
|
|
134
|
+
if len(compressed) < len(data):
|
|
135
|
+
return compressed
|
|
136
|
+
except Exception:
|
|
137
|
+
pass
|
|
138
|
+
|
|
139
|
+
# Fallback to standard compressor
|
|
140
|
+
return self.compressor.compress(data)
|
|
141
|
+
|
|
142
|
+
def _fast_decompression(self, data: bytes) -> bytes:
|
|
143
|
+
"""Use native decompression if available."""
|
|
144
|
+
if self.crypto_core:
|
|
145
|
+
try:
|
|
146
|
+
# Check if this looks like RLE compressed data
|
|
147
|
+
if len(data) > 0 and data[0] == 0xFF:
|
|
148
|
+
return self.crypto_core.fast_decompress_rle(data)
|
|
149
|
+
except Exception:
|
|
150
|
+
pass
|
|
151
|
+
|
|
152
|
+
# Fallback to standard compressor
|
|
153
|
+
return self.compressor.decompress(data)
|
|
154
|
+
|
|
155
|
+
def _fast_xor_encryption(self, data: bytes, key: bytes) -> bytes:
|
|
156
|
+
"""Use native XOR if available for additional obfuscation."""
|
|
157
|
+
if self.crypto_core:
|
|
158
|
+
try:
|
|
159
|
+
return self.crypto_core.fast_xor(data, key)
|
|
160
|
+
except Exception:
|
|
161
|
+
pass
|
|
162
|
+
|
|
163
|
+
# Fallback to Python XOR
|
|
164
|
+
result = bytearray(data)
|
|
165
|
+
for i in range(len(result)):
|
|
166
|
+
result[i] ^= key[i % len(key)]
|
|
167
|
+
return bytes(result)
|
|
168
|
+
|
|
169
|
+
def _fast_hash(self, data: bytes) -> bytes:
|
|
170
|
+
"""Use native SHA-256 if available."""
|
|
171
|
+
if self.hash_algorithms:
|
|
172
|
+
try:
|
|
173
|
+
return self.hash_algorithms.fast_sha256(data)
|
|
174
|
+
except Exception:
|
|
175
|
+
pass
|
|
176
|
+
|
|
177
|
+
# Fallback to standard hash
|
|
178
|
+
import hashlib
|
|
179
|
+
return hashlib.sha256(data).digest()
|
|
180
|
+
|
|
181
|
+
def _fast_hmac(self, key: bytes, data: bytes) -> bytes:
|
|
182
|
+
"""Use native HMAC if available."""
|
|
183
|
+
if self.hash_algorithms:
|
|
184
|
+
try:
|
|
185
|
+
return self.hash_algorithms.fast_hmac_sha256(key, data)
|
|
186
|
+
except Exception:
|
|
187
|
+
pass
|
|
188
|
+
|
|
189
|
+
# Fallback to standard HMAC
|
|
190
|
+
import hmac
|
|
191
|
+
import hashlib
|
|
192
|
+
return hmac.new(key, data, hashlib.sha256).digest()
|
|
193
|
+
|
|
194
|
+
def _fast_custom_encoding(self, data: bytes, charset: str) -> str:
|
|
195
|
+
"""Use native base conversion if available."""
|
|
196
|
+
if self.crypto_core:
|
|
197
|
+
try:
|
|
198
|
+
return self.crypto_core.base_convert_encode(data, charset)
|
|
199
|
+
except Exception:
|
|
200
|
+
pass
|
|
201
|
+
|
|
202
|
+
# Fallback to custom encoder
|
|
203
|
+
if self.custom_encoder and self.custom_encoder.charset == charset:
|
|
204
|
+
return self.custom_encoder.encode(data)
|
|
205
|
+
|
|
206
|
+
temp_encoder = CustomEncoder(charset=charset)
|
|
207
|
+
return temp_encoder.encode(data)
|
|
208
|
+
|
|
209
|
+
def _calculate_entropy(self, data: bytes) -> float:
|
|
210
|
+
"""Calculate data entropy using native library if available."""
|
|
211
|
+
if self.crypto_core:
|
|
212
|
+
try:
|
|
213
|
+
return self.crypto_core.calculate_entropy(data)
|
|
214
|
+
except Exception:
|
|
215
|
+
pass
|
|
216
|
+
|
|
217
|
+
# Fallback to Python implementation
|
|
218
|
+
if not data:
|
|
219
|
+
return 0.0
|
|
220
|
+
|
|
221
|
+
freq = {}
|
|
222
|
+
for byte in data:
|
|
223
|
+
freq[byte] = freq.get(byte, 0) + 1
|
|
224
|
+
|
|
225
|
+
entropy = 0.0
|
|
226
|
+
length = len(data)
|
|
227
|
+
for count in freq.values():
|
|
228
|
+
p = count / length
|
|
229
|
+
if p > 0:
|
|
230
|
+
# Use approximation: log2(p) ≈ (p.bit_length() - 1) for integers
|
|
231
|
+
# For floats, we'll use a simple approximation
|
|
232
|
+
import math
|
|
233
|
+
entropy -= p * math.log2(p)
|
|
234
|
+
|
|
235
|
+
return entropy
|
|
236
|
+
|
|
237
|
+
def compress_and_encrypt(self, data: Union[str, bytes],
|
|
238
|
+
output_format: str = 'binary',
|
|
239
|
+
use_native_optimizations: bool = True) -> Union[bytes, str]:
|
|
240
|
+
"""
|
|
241
|
+
Compress and encrypt data with native optimizations.
|
|
242
|
+
|
|
243
|
+
Args:
|
|
244
|
+
data: Data to compress and encrypt.
|
|
245
|
+
output_format: Output format ('binary', 'custom', 'steganographic').
|
|
246
|
+
use_native_optimizations: Use native libraries for optimization.
|
|
247
|
+
|
|
248
|
+
Returns:
|
|
249
|
+
Union[bytes, str]: Encrypted compressed data.
|
|
250
|
+
"""
|
|
251
|
+
try:
|
|
252
|
+
# Convert string to bytes if necessary
|
|
253
|
+
if isinstance(data, str):
|
|
254
|
+
data_bytes = data.encode('utf-8')
|
|
255
|
+
else:
|
|
256
|
+
data_bytes = data
|
|
257
|
+
|
|
258
|
+
# Step 1: Analyze data for optimal compression
|
|
259
|
+
entropy = self._calculate_entropy(data_bytes)
|
|
260
|
+
|
|
261
|
+
# Step 2: Compress data (with native optimization if available)
|
|
262
|
+
if use_native_optimizations and self.is_native_available():
|
|
263
|
+
compressed_data = self._fast_compression(data_bytes)
|
|
264
|
+
else:
|
|
265
|
+
compressed_data = self.compressor.compress(data_bytes)
|
|
266
|
+
|
|
267
|
+
# Step 3: Generate encryption key with native optimization
|
|
268
|
+
salt = self._generate_salt()
|
|
269
|
+
if use_native_optimizations and self.hash_algorithms:
|
|
270
|
+
key = self._fast_key_derivation(self.password, salt, self.key_manager.iterations, 32)
|
|
271
|
+
else:
|
|
272
|
+
key = self.key_manager.derive_key(self.password, salt, 32)
|
|
273
|
+
|
|
274
|
+
# Step 4: Apply additional XOR obfuscation with native optimization
|
|
275
|
+
if use_native_optimizations and self.crypto_core:
|
|
276
|
+
xor_key = self._fast_hash(key + salt)[:16] # 16-byte XOR key
|
|
277
|
+
obfuscated_data = self._fast_xor_encryption(compressed_data, xor_key)
|
|
278
|
+
else:
|
|
279
|
+
obfuscated_data = compressed_data
|
|
280
|
+
|
|
281
|
+
# Step 5: Encrypt data
|
|
282
|
+
encrypted_data = self.encryptor.encrypt(obfuscated_data, self.password)
|
|
283
|
+
|
|
284
|
+
# Step 6: Apply custom encoding if requested
|
|
285
|
+
if output_format == 'binary':
|
|
286
|
+
return encrypted_data
|
|
287
|
+
elif output_format == 'custom' and self.custom_encoder:
|
|
288
|
+
if use_native_optimizations and self.crypto_core:
|
|
289
|
+
return self._fast_custom_encoding(encrypted_data, self.custom_encoder.charset)
|
|
290
|
+
else:
|
|
291
|
+
return self.custom_encoder.encode(encrypted_data)
|
|
292
|
+
elif output_format == 'steganographic' and self.custom_encoder:
|
|
293
|
+
return self.custom_encoder.create_steganographic_text(encrypted_data)
|
|
294
|
+
else:
|
|
295
|
+
return encrypted_data
|
|
296
|
+
|
|
297
|
+
except Exception as e:
|
|
298
|
+
raise EncrypterError(
|
|
299
|
+
f"Enhanced compression failed: {str(e)}",
|
|
300
|
+
details={
|
|
301
|
+
"operation": "compress_and_encrypt",
|
|
302
|
+
"native_used": use_native_optimizations and self.is_native_available(),
|
|
303
|
+
"error": str(e)
|
|
304
|
+
}
|
|
305
|
+
)
|
|
306
|
+
|
|
307
|
+
def decrypt_and_decompress(self, data: Union[bytes, str],
|
|
308
|
+
input_format: str = 'binary',
|
|
309
|
+
use_native_optimizations: bool = True) -> bytes:
|
|
310
|
+
"""
|
|
311
|
+
Decrypt and decompress data with native optimizations.
|
|
312
|
+
|
|
313
|
+
Args:
|
|
314
|
+
data: Encrypted compressed data to decrypt and decompress.
|
|
315
|
+
input_format: Input format ('binary', 'custom', 'steganographic').
|
|
316
|
+
use_native_optimizations: Use native libraries for optimization.
|
|
317
|
+
|
|
318
|
+
Returns:
|
|
319
|
+
bytes: Original decompressed data.
|
|
320
|
+
"""
|
|
321
|
+
try:
|
|
322
|
+
# Step 1: Decode from custom format if necessary
|
|
323
|
+
if input_format == 'custom' and self.custom_encoder and isinstance(data, str):
|
|
324
|
+
encrypted_data = self.custom_encoder.decode(data)
|
|
325
|
+
elif input_format == 'binary':
|
|
326
|
+
encrypted_data = data
|
|
327
|
+
else:
|
|
328
|
+
encrypted_data = data
|
|
329
|
+
|
|
330
|
+
# Step 2: Decrypt data
|
|
331
|
+
decrypted_data = self.encryptor.decrypt(encrypted_data, self.password)
|
|
332
|
+
|
|
333
|
+
# Step 3: Remove XOR obfuscation if it was applied
|
|
334
|
+
if use_native_optimizations and self.crypto_core:
|
|
335
|
+
# Try to detect if XOR was applied by checking entropy
|
|
336
|
+
entropy = self._calculate_entropy(decrypted_data)
|
|
337
|
+
if entropy > 7.0: # High entropy suggests XOR was applied
|
|
338
|
+
# Reconstruct XOR key
|
|
339
|
+
salt = encrypted_data[:16] # Assume salt is in first 16 bytes
|
|
340
|
+
key = self._fast_key_derivation(self.password, salt, self.key_manager.iterations, 32)
|
|
341
|
+
xor_key = self._fast_hash(key + salt)[:16]
|
|
342
|
+
deobfuscated_data = self._fast_xor_encryption(decrypted_data, xor_key)
|
|
343
|
+
else:
|
|
344
|
+
deobfuscated_data = decrypted_data
|
|
345
|
+
else:
|
|
346
|
+
deobfuscated_data = decrypted_data
|
|
347
|
+
|
|
348
|
+
# Step 4: Decompress data (with native optimization if available)
|
|
349
|
+
if use_native_optimizations and self.is_native_available():
|
|
350
|
+
decompressed_data = self._fast_decompression(deobfuscated_data)
|
|
351
|
+
else:
|
|
352
|
+
decompressed_data = self.compressor.decompress(deobfuscated_data)
|
|
353
|
+
|
|
354
|
+
return decompressed_data
|
|
355
|
+
|
|
356
|
+
except Exception as e:
|
|
357
|
+
raise EncrypterError(
|
|
358
|
+
f"Enhanced decompression failed: {str(e)}",
|
|
359
|
+
details={
|
|
360
|
+
"operation": "decrypt_and_decompress",
|
|
361
|
+
"native_used": use_native_optimizations and self.is_native_available(),
|
|
362
|
+
"error": str(e)
|
|
363
|
+
}
|
|
364
|
+
)
|
|
365
|
+
|
|
366
|
+
def _generate_salt(self) -> bytes:
|
|
367
|
+
"""Generate cryptographically secure salt."""
|
|
368
|
+
if self.crypto_core:
|
|
369
|
+
try:
|
|
370
|
+
return self.crypto_core.secure_random_bytes(16)
|
|
371
|
+
except Exception:
|
|
372
|
+
pass
|
|
373
|
+
|
|
374
|
+
# Fallback to standard random
|
|
375
|
+
import secrets
|
|
376
|
+
return secrets.token_bytes(16)
|
|
377
|
+
|
|
378
|
+
def benchmark_native_vs_python(self, data_size: int = 1024, iterations: int = 100) -> Dict[str, Any]:
|
|
379
|
+
"""
|
|
380
|
+
Benchmark native vs Python implementations.
|
|
381
|
+
|
|
382
|
+
Args:
|
|
383
|
+
data_size: Size of test data in bytes.
|
|
384
|
+
iterations: Number of iterations for benchmarking.
|
|
385
|
+
|
|
386
|
+
Returns:
|
|
387
|
+
Dict[str, Any]: Benchmark results.
|
|
388
|
+
"""
|
|
389
|
+
import time
|
|
390
|
+
import secrets
|
|
391
|
+
|
|
392
|
+
# Generate test data
|
|
393
|
+
test_data = secrets.token_bytes(data_size)
|
|
394
|
+
|
|
395
|
+
results = {
|
|
396
|
+
'data_size': data_size,
|
|
397
|
+
'iterations': iterations,
|
|
398
|
+
'native_available': self.is_native_available()
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
if not self.is_native_available():
|
|
402
|
+
results['error'] = 'Native libraries not available'
|
|
403
|
+
return results
|
|
404
|
+
|
|
405
|
+
# Benchmark compression
|
|
406
|
+
if self.crypto_core:
|
|
407
|
+
# Native compression
|
|
408
|
+
start_time = time.time()
|
|
409
|
+
for _ in range(iterations):
|
|
410
|
+
compressed = self.crypto_core.fast_compress_rle(test_data)
|
|
411
|
+
native_compress_time = time.time() - start_time
|
|
412
|
+
|
|
413
|
+
# Python compression
|
|
414
|
+
start_time = time.time()
|
|
415
|
+
for _ in range(iterations):
|
|
416
|
+
compressed = self.compressor.compress(test_data)
|
|
417
|
+
python_compress_time = time.time() - start_time
|
|
418
|
+
|
|
419
|
+
results['compression'] = {
|
|
420
|
+
'native_time': native_compress_time,
|
|
421
|
+
'python_time': python_compress_time,
|
|
422
|
+
'speedup': python_compress_time / native_compress_time if native_compress_time > 0 else 0
|
|
423
|
+
}
|
|
424
|
+
|
|
425
|
+
# Benchmark hashing
|
|
426
|
+
if self.hash_algorithms:
|
|
427
|
+
# Native hashing
|
|
428
|
+
start_time = time.time()
|
|
429
|
+
for _ in range(iterations):
|
|
430
|
+
hash_result = self.hash_algorithms.fast_sha256(test_data)
|
|
431
|
+
native_hash_time = time.time() - start_time
|
|
432
|
+
|
|
433
|
+
# Python hashing
|
|
434
|
+
import hashlib
|
|
435
|
+
start_time = time.time()
|
|
436
|
+
for _ in range(iterations):
|
|
437
|
+
hash_result = hashlib.sha256(test_data).digest()
|
|
438
|
+
python_hash_time = time.time() - start_time
|
|
439
|
+
|
|
440
|
+
results['hashing'] = {
|
|
441
|
+
'native_time': native_hash_time,
|
|
442
|
+
'python_time': python_hash_time,
|
|
443
|
+
'speedup': python_hash_time / native_hash_time if native_hash_time > 0 else 0
|
|
444
|
+
}
|
|
445
|
+
|
|
446
|
+
# Benchmark key derivation
|
|
447
|
+
if self.hash_algorithms:
|
|
448
|
+
password = b"test_password"
|
|
449
|
+
salt = b"test_salt_16bytes"
|
|
450
|
+
|
|
451
|
+
# Native PBKDF2
|
|
452
|
+
start_time = time.time()
|
|
453
|
+
for _ in range(10): # Fewer iterations for expensive operation
|
|
454
|
+
key = self.hash_algorithms.fast_pbkdf2(password, salt, 1000, 32)
|
|
455
|
+
native_kdf_time = time.time() - start_time
|
|
456
|
+
|
|
457
|
+
# Python PBKDF2
|
|
458
|
+
start_time = time.time()
|
|
459
|
+
for _ in range(10):
|
|
460
|
+
key = self.key_manager.derive_key("test_password", salt, 32)
|
|
461
|
+
python_kdf_time = time.time() - start_time
|
|
462
|
+
|
|
463
|
+
results['key_derivation'] = {
|
|
464
|
+
'native_time': native_kdf_time,
|
|
465
|
+
'python_time': python_kdf_time,
|
|
466
|
+
'speedup': python_kdf_time / native_kdf_time if native_kdf_time > 0 else 0
|
|
467
|
+
}
|
|
468
|
+
|
|
469
|
+
return results
|
|
470
|
+
|
|
471
|
+
def get_native_info(self) -> Dict[str, Any]:
|
|
472
|
+
"""Get information about native library availability and performance."""
|
|
473
|
+
info = {
|
|
474
|
+
'native_support': NATIVE_SUPPORT,
|
|
475
|
+
'prefer_native': self.prefer_native,
|
|
476
|
+
'native_available': self.is_native_available(),
|
|
477
|
+
'libraries': {}
|
|
478
|
+
}
|
|
479
|
+
|
|
480
|
+
if self.native_manager:
|
|
481
|
+
manager_info = self.native_manager.get_info()
|
|
482
|
+
info.update(manager_info)
|
|
483
|
+
|
|
484
|
+
# Add performance info
|
|
485
|
+
if self.hash_algorithms:
|
|
486
|
+
try:
|
|
487
|
+
perf_time = self.hash_algorithms.benchmark_hash_performance(1024, 100)
|
|
488
|
+
info['hash_performance'] = {
|
|
489
|
+
'time_seconds': perf_time,
|
|
490
|
+
'throughput_mbps': (1024 * 100 / (1024 * 1024)) / perf_time if perf_time > 0 else 0
|
|
491
|
+
}
|
|
492
|
+
except Exception as e:
|
|
493
|
+
info['hash_performance'] = {'error': str(e)}
|
|
494
|
+
|
|
495
|
+
return info
|
|
496
|
+
|
|
497
|
+
def get_info(self) -> Dict[str, Any]:
|
|
498
|
+
"""Get comprehensive information about the EnhancedCompressor."""
|
|
499
|
+
base_info = {
|
|
500
|
+
'version': '2.0.0',
|
|
501
|
+
'type': 'EnhancedCompressor',
|
|
502
|
+
'configuration': self.config,
|
|
503
|
+
}
|
|
504
|
+
|
|
505
|
+
# Add native library info
|
|
506
|
+
base_info['native'] = self.get_native_info()
|
|
507
|
+
|
|
508
|
+
# Add standard component info
|
|
509
|
+
base_info['compressor_info'] = self.compressor.get_info()
|
|
510
|
+
base_info['encryptor_info'] = self.encryptor.get_info()
|
|
511
|
+
base_info['key_manager_info'] = self.key_manager.get_info()
|
|
512
|
+
|
|
513
|
+
if self.custom_encoder:
|
|
514
|
+
base_info['custom_encoder_info'] = self.custom_encoder.get_charset_info()
|
|
515
|
+
|
|
516
|
+
return base_info
|
|
517
|
+
|
|
518
|
+
def __repr__(self) -> str:
|
|
519
|
+
"""String representation of the EnhancedCompressor."""
|
|
520
|
+
native_status = "native" if self.is_native_available() else "python"
|
|
521
|
+
charset_info = f", charset={self.custom_encoder.charset}" if self.custom_encoder else ""
|
|
522
|
+
|
|
523
|
+
return (f"EnhancedCompressor("
|
|
524
|
+
f"compression={self.compressor.algorithm.value}, "
|
|
525
|
+
f"encryption={self.encryptor.algorithm.value}, "
|
|
526
|
+
f"mode={native_status}"
|
|
527
|
+
f"{charset_info})")
|
|
528
|
+
|
|
529
|
+
def __str__(self) -> str:
|
|
530
|
+
"""Human-readable string representation."""
|
|
531
|
+
base_str = (f"Enhanced Compressor with {self.compressor.algorithm.value.upper()} compression "
|
|
532
|
+
f"and {self.encryptor.algorithm.value.upper()} encryption")
|
|
533
|
+
|
|
534
|
+
if self.is_native_available():
|
|
535
|
+
base_str += " (native acceleration enabled)"
|
|
536
|
+
else:
|
|
537
|
+
base_str += " (pure Python mode)"
|
|
538
|
+
|
|
539
|
+
if self.custom_encoder:
|
|
540
|
+
base_str += f" using custom charset '{self.custom_encoder.charset}'"
|
|
541
|
+
|
|
542
|
+
return base_str
|