### cryptcp.exe signature verification
### 1
Алгоритм проверки подписи CAdES-XL с учетом того, что TSP должен быть действительным при проверке, а сертификаты подписанта могут быть просрочены.
## Алгоритм проверки подписи с cryptcp.exe
```mermaid
graph TB
A[Начало проверки] --> B[Подготовка окружения]
B --> C[Проверка TSP-метки]
C --> D{TSP действителен?}
D -->|Нет| E[❌ Подпись недействительна]
D -->|Да| F[Проверка целостности]
F --> G{Подпись соответствует документу?}
G -->|Нет| E
G -->|Да| H[Проверка исторической действительности]
H --> I{Сертификат был действителен при подписании?}
I -->|Нет| E
I -->|Да| J[✅ Подпись действительна]
```
## Детальный алгоритм проверки
### 1. Подготовка окружения для проверки
**Обязательные условия:**
- Установлен КриптоПРО CSP
- Установлены актуальные доверенные корневые сертификаты для TSA
- Доступ к интернету для проверки TSP
```bash
# Проверка установки КриптоПРО
where cryptcp.exe
# Проверка доступности TSP-сервиса
ping tsp.tensor.ru
```
### 2. Проверка TSP-метки (критически важно)
```bash
# Команда проверки с акцентом на TSP
cryptcp -verify -cadestype XL -v "signature.sig" "document.pdf"
```
**Что проверяет cryptcp в TSP:**
- Действительность сертификата TSA на момент проверки
- Цепочку доверия TSA до доверенного корневого УЦ
- Корректность временной метки
- Соответствие хэша подписи
### 3. Анализ результатов проверки
```python
import subprocess
import re
def verify_signature(signature_file, document_file):
"""
Функция проверки подписи с анализом TSP
"""
command = [
"cryptcp.exe",
"-verify",
"-cadestype", "XL",
"-v", # Детальный вывод
signature_file,
document_file
]
result = subprocess.run(command, capture_output=True, text=True, encoding='cp866')
return analyze_verification_result(result)
def analyze_verification_result(result):
"""
Анализ вывода cryptcp с акцентом на TSP
"""
output = result.stdout + result.stderr
# Критически важные проверки
checks = {
'tsp_valid': False,
'signature_integrity': False,
'historical_cert_valid': False
}
# Проверка TSP-метки
if re.search(r'Timestamp.*valid|Временная.*метка.*действительна', output, re.IGNORECASE):
checks['tsp_valid'] = True
# Проверка целостности подписи
if re.search(r'signature.*valid|подпись.*действительна', output, re.IGNORECASE):
checks['signature_integrity'] = True
# Проверка исторической действительности сертификата
if re.search(r'certificate.*was.*valid|сертификат.*был.*действителен', output, re.IGNORECASE):
checks['historical_cert_valid'] = True
# Определение итогового результата
if checks['tsp_valid'] and checks['signature_integrity']:
return "✅ Подпись действительна"
else:
return "❌ Подпись недействительна"
```
### 4. Интерпретация кодов возврата cryptcp.exe
```python
def interpret_exit_code(exit_code):
"""
Интерпретация кодов возврата cryptcp.exe
"""
exit_codes = {
0: "✅ Успешная проверка",
1: "❌ Общая ошибка",
2: "❌ Неверный формат подписи",
3: "❌ Проблема с сертификатом",
4: "❌ Ошибка цепочки доверия",
5: "❌ Ошибка проверки целостности"
}
return exit_codes.get(exit_code, f"❌ Неизвестный код ошибки: {exit_code}")
```
## Практические команды для разных сценариев
### Сценарий 1: Базовая проверка
```bash
cryptcp -verify -cadestype XL "document.pdf.sig" "document.pdf"
```
### Сценарий 2: Детальная проверка с фокусом на TSP
```bash
cryptcp -verify -cadestype XL -v -tsp "http://tsp.tensor.ru" "document.pdf.sig" "document.pdf"
```
### Сценарий 3: Проверка с игнорированием просроченных сертификатов подписанта
```bash
# К сожалению, cryptcp не имеет прямого параметра для игнорирования просрочки
# Но можно использовать кастомное хранилище сертификатов
cryptcp -verify -cadestype XL -store "My" "document.pdf.sig" "document.pdf"
```
## Полная программа проверки на Python
```python
import subprocess
import os
from datetime import datetime
class SignatureVerifier:
def __init__(self, cryptcp_path="cryptcp.exe"):
self.cryptcp_path = cryptcp_path
def verify_signature(self, signature_path, document_path):
"""
Полная проверка подписи с акцентом на TSP
"""
print(f"🔍 Проверка подписи: {os.path.basename(signature_path)}")
print(f"📄 Документ: {os.path.basename(document_path)}")
print(f"🕒 Время проверки: {datetime.now()}")
# Проверка существования файлов
if not os.path.exists(signature_path):
return "❌ Файл подписи не найден"
if not os.path.exists(document_path):
return "❌ Файл документа не найден"
# Выполнение проверки
command = [
self.cryptcp_path,
"-verify",
"-cadestype", "XL",
"-v",
signature_path,
document_path
]
try:
result = subprocess.run(
command,
capture_output=True,
text=True,
encoding='cp866',
timeout=30
)
return self.analyze_result(result)
except subprocess.TimeoutExpired:
return "❌ Таймаут проверки"
except FileNotFoundError:
return "❌ cryptcp.exe не найден"
def analyze_result(self, result):
"""
Детальный анализ результатов проверки
"""
analysis = {
'success': result.returncode == 0,
'exit_code': result.returncode,
'tsp_status': 'unknown',
'signature_status': 'unknown',
'certificate_status': 'unknown'
}
output = result.stdout + result.stderr
# Анализ TSP
if 'timestamp verified' in output.lower() or 'временная метка действительна' in output.lower():
analysis['tsp_status'] = 'valid'
elif 'timestamp invalid' in output.lower() or 'временная метка недействительна' in output.lower():
analysis['tsp_status'] = 'invalid'
# Анализ подписи
if 'signature verified' in output.lower() or 'подпись действительна' in output.lower():
analysis['signature_status'] = 'valid'
elif 'signature invalid' in output.lower() or 'подпись недействительна' in output.lower():
analysis['signature_status'] = 'invalid'
# Формирование итогового вердикта
return self.generate_verdict(analysis, output)
def generate_verdict(self, analysis, output):
"""
Формирование итогового заключения на основе анализа
"""
# Критически важные проверки
if analysis['tsp_status'] != 'valid':
return "❌ ПОДПИСЬ НЕДЕЙСТВИТЕЛЬНА: TSP-метка не прошла проверку"
if analysis['signature_status'] != 'valid':
return "❌ ПОДПИСЬ НЕДЕЙСТВИТЕЛЬНА: нарушена целостность подписи"
# Если TSP и подпись действительны - подпись считается действительной
# независимо от статуса сертификата подписанта
if analysis['success']:
return "✅ ПОДПИСЬ ДЕЙСТВИТЕЛЬНА"
else:
# Даже если cryptcp вернул ошибку, но TSP и подпись действительны,
# это может быть из-за просроченного сертификата подписанта
if analysis['tsp_status'] == 'valid' and analysis['signature_status'] == 'valid':
return "✅ ПОДПИСЬ ДЕЙСТВИТЕЛЬНА (TSP подтвержден, сертификат подписанта мог истечь)"
else:
return f"❌ ПОДПИСЬ НЕДЕЙСТВИТЕЛЬНА. Код: {analysis['exit_code']}"
# Использование
if __name__ == "__main__":
verifier = SignatureVerifier()
result = verifier.verify_signature("document.pdf.sig", "document.pdf")
print(result)
```
## Особые случаи и обработка ошибок
### Случай 1: Просрочен сертификат подписанта
```bash
# cryptcp может вернуть ошибку, но если TSP действителен - подпись сохраняет силу
cryptcp -verify ...
# Возвращает код 3, но TSP проверен - подпись ДЕЙСТВИТЕЛЬНА
```
### Случай 2: Недействительный TSP
```bash
# Любая ошибка TSP делает подпись недействительной
cryptcp -verify ...
# TSP не прошел проверку - подпись НЕДЕЙСТВИТЕЛЬНА
```
### Случай 3: Нарушена целостность
```bash
# Изменен документ или подпись
cryptcp -verify ...
# Нарушена целостность - подпись НЕДЕЙСТВИТЕЛЬНА
```
## Выводы:
1. **TSP-метка должна быть действительной ПРИ ПРОВЕРКЕ** - это критически важно
2. **Сертификат подписанта** может быть просрочен - важно только его состояние на момент подписания
3. **Cryptcp.exe** не имеет прямых параметров для игнорирования просрочки сертификатов, но фокус на TSP позволяет корректно оценить юридическую значимость
4. **Алгоритм проверки** должен в первую очередь анализировать статус TSP и целостность подписи
Данный алгоритм обеспечивает корректную проверку юридической значимости электронной подписи в соответствии с требованиями законодательства и учетом долгосрочного хранения документов.
### 2
## Алгоритм проверки электронной подписи с акцентом на TSP
```mermaid
flowchart TD
A[Начало проверки подписи] --> B[Подготовка окружения]
B --> C[Проверка наличия файлов]
C --> D{Файлы существуют?}
D -->|Нет| E[❌ Ошибка: файлы не найдены]
D -->|Да| F[Запуск cryptcp.exe для проверки]
F --> G[Анализ вывода cryptcp]
subgraph G [Анализ результатов]
H[Проверка TSP-метки]
I[Проверка целостности подписи]
J[Проверка сертификата подписанта]
end
H --> K{TSP действителен?}
K -->|Нет| L[❌ Подпись недействительна
TSP не прошел проверку]
K -->|Да| I
I --> M{Подпись соответствует документу?}
M -->|Нет| N[❌ Подпись недействительна
Нарушена целостность]
M -->|Да| J
J --> O{Сертификат был действителен
на момент подписания?}
O -->|Нет| P[❌ Подпись недействительна
Сертификат был недействителен]
O -->|Да| Q[✅ Подпись действительна]
style A fill:#e1f5fe
style L fill:#ffebee
style N fill:#ffebee
style P fill:#ffebee
style Q fill:#e8f5e9
style H fill:#fff3e0
style I fill:#fff3e0
style J fill:#fff3e0
```
## Детализация критических проверок
```mermaid
flowchart TD
A[Детали проверок] --> B[TSP-метка]
A --> C[Целостность подписи]
A --> D[Сертификат подписанта]
subgraph B [Проверка TSP-метки]
B1[Сертификат TSA действителен]
B2[Цепочка доверия TSA построена]
B3[Временная метка корректна]
B4[Хэш подписи соответствует]
end
subgraph C [Проверка целостности]
C1[Подпись соответствует документу]
C2[Формат CAdES-XL корректен]
C3[Хэш документа не изменен]
end
subgraph D [Проверка сертификата подписанта]
D1[Вложенный OCSP-ответ действителен]
D2[Сертификат не был отозван
на момент подписания]
D3[Цепочка была полной
на момент подписания]
end
B --> E{✅ TSP действителен?}
C --> F{✅ Целостность сохранена?}
D --> G{✅ Сертификат был действителен?}
E & F & G --> H[✅ Все проверки пройдены]
style B fill:#fff3e0
style C fill:#fff3e0
style D fill:#fff3e0
style H fill:#e8f5e9
```
## Процесс работы с cryptcp.exe
```mermaid
sequenceDiagram
participant П as Программа проверки
participant C как cryptcp.exe
participant CSP как КриптоПРО CSP
participant T как TSA Сервис
participant Х как Хранилище сертификатов
П->>C: Запуск: cryptcp -verify -cadestype XL -v signature.sig document.pdf
C->>CSP: Декодирование CAdES-XL
C->>CSP: Извлечение TSP-метки
C->>T: Проверка сертификата TSA
T-->>C: Статус сертификата TSA
C->>Х: Поиск корневых сертификатов TSA
Х-->>C: Корневые сертификаты
C->>CSP: Проверка TSP-метки
CSP-->>C: Результат проверки TSP
C->>CSP: Проверка целостности подписи
CSP-->>C: Результат проверки целостности
C->>CSP: Проверка сертификата подписанта
CSP-->>C: Результат проверки сертификата
C-->>П: Код возврата и детальный вывод
П->>П: Анализ результатов с акцентом на TSP
П->>П: Формирование итогового вердикта
```
## Интерпретация результатов
```mermaid
flowchart TD
A[Анализ вывода cryptcp.exe] --> B[Поиск ключевых фраз]
B --> C[TSP-метка]
B --> D[Целостность подписи]
B --> E[Сертификат подписанта]
C --> C1[“timestamp verified”
“временная метка действительна”]
C1 --> C2[✅ TSP действителен]
D --> D1[“signature verified”
“подпись действительна”]
D1 --> D2[✅ Целостность сохранена]
E --> E1[“certificate was valid”
“сертификат был действителен”]
E1 --> E2[✅ Сертификат был действителен]
C2 & D2 --> F[✅ Подпись действительна]
C --> C3[“timestamp invalid”
“временная метка недействительна”]
C3 --> G[❌ Критическая ошибка TSP]
D --> D3[“signature invalid”
“подпись недействительна”]
D3 --> H[❌ Критическая ошибка целостности]
E --> E3[“certificate was invalid”
“сертификат был недействителен”]
E3 --> I[❌ Сертификат был недействителен]
G --> J[❌ Подпись недействительна]
H --> J
I --> J
style F fill:#e8f5e9
style J fill:#ffebee
style C2 fill:#e8f5e9
style D2 fill:#e8f5e9
style E2 fill:#e8f5e9
style G fill:#ffebee
style H fill:#ffebee
style I fill:#ffebee
```
## Критерии юридической значимости
```mermaid
flowchart TD
A[Критерии юридической значимости] --> B[Критически важные]
A --> C[Второстепенные]
B --> B1[TSP действителен при проверке]
B --> B2[Целостность подписи сохранена]
B --> B3[Сертификат был действителен при подписании]
C --> C1[Корневые сертификаты УЦ действительны]
C --> C2[Сертификат подписанта действителен сейчас]
C --> C3[Актуальные OCSP-ответы]
B1 & B2 & B3 --> D[✅ Юридически значимая подпись]
C1 -.->|Не влияет на историческую подпись| D
C2 -.->|Не влияет на историческую подпись| D
C3 -.->|Не влияет на историческую подпись| D
style B fill:#fff3e0
style C fill:#f5f5f5
style D fill:#e8f5e9
```
Этот алгоритм наглядно показывает, что проверка TSP-метки является критически важным этапом, от которого зависит юридическая значимость всей электронной подписи, независимо от текущего статуса других сертификатов.