Ключевое слово в защите информации
КЛЮЧЕВОЕ СЛОВО
в защите информации
Получить ГОСТ TLS-сертификат для домена (SSL-сертификат)
Добро пожаловать, Гость! Чтобы использовать все возможности Вход или Регистрация.

Уведомление

Icon
Error

Опции
К последнему сообщению К первому непрочитанному
Offline YashinSergey  
#1 Оставлено : 28 мая 2008 г. 18:58:41(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Добрый день.

Появилась одна проблема а вместе с ней и вопрос:
1. есть текст клиента
2. есть его подпись на этот текст
3. есть его же публичный ключ.

подписывался текст следующим образом: брался хеш текста а уже хеш подписывался.

Выполнялось это через CryptoPro C++.

Вопрос в следующем - почему на JCP при проверке тех же данных с помощью Signature -> verify и ключа клиента
проверка подписи не проходит. (OID для хеша тот же) ?

Это связанно с тем, что используется для проверки демо версия JCP или нет ?
Offline Русев Андрей  
#2 Оставлено : 28 мая 2008 г. 20:36:45(UTC)
Андрей Русев

Статус: Сотрудник

Группы: Администраторы, Участники
Зарегистрирован: 16.04.2008(UTC)
Сообщений: 932

Сказал(а) «Спасибо»: 4 раз
Поблагодарили: 254 раз в 195 постах
Detached-подпись JCP имеет инверсный порядок байт по сравнению с CSP. Для встречной работы можно использовать специальный класс для совместимости:
Signature.getInstance(JCP.CRYPTOPRO_SIGN_NAME, JCP.PROVIDER_NAME);

либо переворачивать подпись самостоятельно:
byte[] sign = readFile();
sign = ru.CryptoPro.JCP.tools.Array.invByteOrderB(sign);
s = Signature.getInstance(JCP.GOST_EL_SIGN_NAME, JCP.PROVIDER_NAME);
...
s.verify(sign);
Официальная техподдержка. Официальная база знаний.
Offline YashinSergey  
#3 Оставлено : 28 мая 2008 г. 20:48:46(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Всё равно не работает :-(, вот мой код:

public class CheckRealSign {

private static String clientCertPath = "C:\\certs\\sign\\client.cer";
private static String clientSignPath = "C:\\certs\\sign\\client.sign";
private static String clientTextPath = "C:\\certs\\sign\\client_text.txt";

String signAlghorithmName = "GOST3411withGOST3410EL";
String digestAlgorithmName = "GOST3411";

private FileInputStream isClientCertPath;
private FileInputStream isClientSignPath;
private FileInputStream isClientTextPath;
CertificateFactory cf = null;
Certificate certClient = null;

OID digestOID;

public CheckRealSign() {
digestOID = new OID("1.2.643.2.2.30.1");
}

public void start() {
try {
isClientCertPath = new FileInputStream(clientCertPath);
isClientSignPath = new FileInputStream(clientSignPath);
isClientTextPath = new FileInputStream(clientTextPath);
} catch (FileNotFoundException e) {
System.out.println("Error: " + e.toString());
return;
}

try {
cf = CertificateFactory.getInstance("X509");
certClient = cf.generateCertificate(isClientCertPath);
} catch (CertificateException e) {
System.out.println("Error cert: " + e.toString());
return;
}

byte[] clientTextByte;

try {
clientTextByte = new byte[isClientTextPath.available()];
isClientTextPath.read(clientTextByte);
} catch (IOException e) {
System.out.println("Error: " + e.toString());
return;
}

byte[] clientSignByte;

try {
clientSignByte = new byte[isClientSignPath.available()];
isClientSignPath.read(clientSignByte);
} catch (IOException e) {
System.out.println("Error: " + e.toString());
return;
}

clientSignByte = ru.CryptoPro.JCP.tools.Array.invByteOrderB(clientSignByte);

MessageDigest digest = null;

try {
digest = MessageDigest.getInstance(digestAlgorithmName);
} catch (NoSuchAlgorithmException e) {
System.out.println("Error: " + e.toString());
return;
}

if(digest == null) {
System.out.println("Error: digest is null.");
return;
}

GostDigest gostDigest = (GostDigest)digest;
gostDigest.reset(digestOID);

ByteArrayInputStream stream = new ByteArrayInputStream(clientTextByte);
DigestInputStream digestStream = new DigestInputStream(stream, gostDigest);
try {
while (digestStream.available() != 0) digestStream.read();
} catch (IOException e) {
System.out.println("Error: " + e.toString());
return;
}
byte[] resultDigest = gostDigest.digest();

Signature sig;

ParamsInterface digestParams = AlgIdSpec.getDefaultDigestParams();
digestParams.setDefault(digestOID);

try {
sig = Signature.getInstance(signAlghorithmName);
sig.initVerify(certClient.getPublicKey());
sig.setParameter(digestParams);
sig.update(resultDigest);
boolean verifies = sig.verify(clientSignByte);
if(verifies) {
System.out.println("Client sign check OK, sign right.");
} else {
System.out.println("Client sign check Fail, sign wrong.");
}
} catch (NoSuchAlgorithmException e) {
System.out.println("Error: " + e.toString());
return;
} catch (InvalidKeyException e) {
System.out.println("Error: " + e.toString());
return;
} catch (SignatureException e) {
System.out.println("Error: " + e.toString());
return;
} catch (InvalidAlgorithmParameterException e) {
System.out.println("Error: " + e.toString());
return;
}
}

public static void main(String[] args) throws Exception {
CheckRealSign checkRealSign = new CheckRealSign();
checkRealSign.start();
}
}


Правильный ли он ?
Offline Ольга  
#4 Оставлено : 28 мая 2008 г. 20:59:32(UTC)
Ольга

Статус: Активный участник

Группы: Участники
Зарегистрирован: 23.01.2008(UTC)
Сообщений: 207

Поблагодарили: 3 раз в 3 постах
какие ошибки выдает?
Offline YashinSergey  
#5 Оставлено : 28 мая 2008 г. 21:03:00(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Ольга написал:
какие ошибки выдает?


Код ошибки не выдает, дело в том, что при проверке подписи из файла "client.sign" на текст из файла "client_text.txt", с сертификатом "client.cer",
выдается ошибка, что подпись неверна. Подпись в файле "client.sign" создавалась с помощью CSP.
Подпись однозначно верна, как и сертификат.

Почему на JCP выдает, что подпись не верна ?
Offline Ольга  
#6 Оставлено : 28 мая 2008 г. 21:04:12(UTC)
Ольга

Статус: Активный участник

Группы: Участники
Зарегистрирован: 23.01.2008(UTC)
Сообщений: 207

Поблагодарили: 3 раз в 3 постах
а вы CSP эту подпись проверяли?
Offline YashinSergey  
#7 Оставлено : 28 мая 2008 г. 21:06:48(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Проверяли, под CSP работает (подпись верна).

Отредактировано пользователем 28 мая 2008 г. 21:08:05(UTC)  | Причина: Не указана

Offline Ольга  
#8 Оставлено : 28 мая 2008 г. 21:19:04(UTC)
Ольга

Статус: Активный участник

Группы: Участники
Зарегистрирован: 23.01.2008(UTC)
Сообщений: 207

Поблагодарили: 3 раз в 3 постах
вот рабочий пример:
Код:
public static void main(String[] args) throws Exception {
//csptest.exe -keyset -sign GOST -container 111 -in e:\text -out e:\text.sign -keytype exchange
    final byte[] buffer = Array.readFile("E:\\text");
    final byte[] sig = Array.readFile("E:\\text.sign");
    final CertificateFactory cf = CertificateFactory.getInstance("X509");
    final Certificate cert =
            cf.generateCertificate(new FileInputStream("E:\\111.cer"));
    final PublicKey pub = cert.getPublicKey();
    //var 1
    final Signature s = Signature.getInstance(JCP.CRYPTOPRO_SIGN_NAME,
            JCP.PROVIDER_NAME);
    s.initVerify(pub);
    s.update(buffer);
    final boolean verifies = s.verify(sig);
    System.out.println("signature verifies: " + verifies);
    if (!verifies) {
        throw new Exception("Signature was not verified");
    }
    //var 2
    final Signature ss = Signature.getInstance(JCP.GOST_EL_SIGN_NAME,
            JCP.PROVIDER_NAME);
    ss.initVerify(pub);
    ss.update(buffer);
    final byte[] invSig = Array.invByteOrderB(sig);
    final boolean verif = ss.verify(invSig);
    System.out.println("signature verifies: " + verif);
    if (!verif) {
        throw new Exception("Signature was not verified");
    }

}
Offline YashinSergey  
#9 Оставлено : 28 мая 2008 г. 21:31:01(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Этот пример не подходит для моей ситуации - подпись делается по хешу, а не по самому тексту, в моем коде это и так описано.

пробовал добавить Signature.getInstance(JCP.GOST_EL_SIGN_NAME, JCP.PROVIDER_NAME); и Signature.getInstance(JCP.CRYPTOPRO_SIGN_NAME, JCP.PROVIDER_NAME);
результат - тот же самый.

Вот только раскопали Array.invByteOrderB(sig);
что ещё может быть ? почему не работает на JCP ?

Отредактировано пользователем 28 мая 2008 г. 21:38:19(UTC)  | Причина: Не указана

Offline YashinSergey  
#10 Оставлено : 28 мая 2008 г. 22:06:04(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Может ли всё выше перечисленное происходить по причине использования DEMO версии JCP ?

Отредактировано пользователем 28 мая 2008 г. 22:06:37(UTC)  | Причина: Не указана

Offline Ольга  
#11 Оставлено : 28 мая 2008 г. 22:20:49(UTC)
Ольга

Статус: Активный участник

Группы: Участники
Зарегистрирован: 23.01.2008(UTC)
Сообщений: 207

Поблагодарили: 3 раз в 3 постах
для подписи/проверки подписи файла с хешем, надо использовать код:

Код:
public static void main(String[] args) throws Exception {
//csptest -keys -hash GOST -in e:\text -hashout e:\text.hsh
//csptest.exe -keyset -sign GOST -container 111 -in e:\text.hsh -out e:\text.hsh.sign -keytype exchange
    final byte[] buffer = Array.readFile("E:\\text.hsh");
    final byte[] sig = Array.readFile("E:\\text.hsh.sign");
    final CertificateFactory cf = CertificateFactory.getInstance("X509");
    final Certificate cert =
            cf.generateCertificate(new FileInputStream("E:\\111.cer"));
    final PublicKey pub = cert.getPublicKey();
    //var 1
    final Signature sss = Signature.getInstance(JCP.CRYPTOPRO_SIGN_NAME,
            JCP.PROVIDER_NAME);
    sss.initVerify(pub);
    sss.update(buffer);
    final boolean verifies = sss.verify(sig);
    System.out.println("signature verifies: " + verifies);
    if (!verifies) {
        throw new Exception("Signature was not verified");
    }
    //var 2
    final Signature ss = Signature.getInstance(JCP.GOST_EL_SIGN_NAME,
            JCP.PROVIDER_NAME);
    ss.initVerify(pub);
    ss.update(buffer);
    final byte[] invSig = Array.invByteOrderB(sig);
    final boolean verif = ss.verify(invSig);
    System.out.println("signature verifies: " + verif);
    if (!verif) {
        throw new Exception("Signature was not verified");
    }

}


ps: Пишите один try {} catch {} на весь код функции. Строку с ошибкой скажет e.printStackTrace().

Отредактировано пользователем 29 мая 2008 г. 14:40:51(UTC)  | Причина: Не указана

Offline YashinSergey  
#12 Оставлено : 28 мая 2008 г. 22:35:29(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Строка в вашем примере "csptest -keys -hash GOST -in e:\text -hashout e:\text.hsh"
у меня лично не работает нормально, вылетает окошко с просьбой выбрать ключевой
носитель, в ключевом носителе что только не выбираю - толку нет, один только вопрос -
нафига козе баян ? (для генерации хеша зачем ключевой носитель и байда с окошками ?).

В общем пример ваш использовать нет возможности. Да и потом в моем примере кода,
всё тоже самое, не пойму зачем одно и тоже переписывать не один раз.

И пожалуйста не предлагайте использовать для генерации всякую ерунду типа csptest который мало
того что не работает по человечески, ко всему этому мы ещё и пишем на языке Java, поэтому давайте им и ограничимся.

Скажите лучше в чем причина ? Как решить ?
Offline Ольга  
#13 Оставлено : 29 мая 2008 г. 16:40:41(UTC)
Ольга

Статус: Активный участник

Группы: Участники
Зарегистрирован: 23.01.2008(UTC)
Сообщений: 207

Поблагодарили: 3 раз в 3 постах
Если бы все сделали правильно, то все работало бы. отличие подписи в JCP и CSP только в этом:
olin написал:
Detached-подпись JCP имеет инверсный порядок байт по сравнению с CSP.
Offline Русев Андрей  
#14 Оставлено : 30 мая 2008 г. 16:55:52(UTC)
Андрей Русев

Статус: Сотрудник

Группы: Администраторы, Участники
Зарегистрирован: 16.04.2008(UTC)
Сообщений: 932

Сказал(а) «Спасибо»: 4 раз
Поблагодарили: 254 раз в 195 постах
Окошко с просьбой выбрать ключевоей носитель возникает в случае, если не создан контейнер по умолчанию. Операцию хеширования можно делать и на verify_context, тогда окошек не будет:
csptest -keys -hash GOST -in e:\text -hashout e:\text.hsh -verifycontext

P.S. Если вам говорят использовать csptest, значит есть подозрения, что вы наделали ошибок не только на Java, но и на Си. Ваш код очень плохо оформлен, поэтому искать в нём ошибку ни у кого нет желания. Вместо этого вам предалгают простое и правильное решение, поняв которое вы сами найдёте свои ошибки.

P.P.S. Ваша ошибка в понимании sig.update(resultDigest). Код будет работать, если clientTextPath = "C:\\certs\\sign\\client_text.txt.hash"; будет содержать хеш файла "C:\\certs\\sign\\client_text.txt". О чём вам и сказала Ольга. Другими словами, в CSP вы подписываете хеш, а не сам файл (на уровне криптографических объектов - хеш хеша), это логическая ошибка.
Официальная техподдержка. Официальная база знаний.
Offline YashinSergey  
#15 Оставлено : 31 мая 2008 г. 0:44:20(UTC)
YashinSergey

Статус: Участник

Группы: Участники
Зарегистрирован: 26.05.2008(UTC)
Сообщений: 23
Откуда: Москва

Во первых - спасибо за csptest -keys -hash GOST -in e:\text -hashout e:\text.hsh -verifycontext
а по поводу кода - код тестовый, а не реальная программа.
По поводу желания рыться в коде - мы ваши клиенты, и платим вам деньги из которых вам начисляется заработная плата,
схема надеюсь понятна, поэтому у вас не может быть желания или нежелания - есть работа за которую мы вам платим.

Спасибо за поддержку.

Отредактировано пользователем 31 мая 2008 г. 0:53:50(UTC)  | Причина: Не указана

Offline Русев Андрей  
#16 Оставлено : 2 июня 2008 г. 15:11:23(UTC)
Андрей Русев

Статус: Сотрудник

Группы: Администраторы, Участники
Зарегистрирован: 16.04.2008(UTC)
Сообщений: 932

Сказал(а) «Спасибо»: 4 раз
Поблагодарили: 254 раз в 195 постах
Мы оказываем платную техническую поддержку по использованию наших продуктов, но не встраиванию. В дальнейшем по вопросам тех.поддержки обращайтесь в письменной форме с указанием номеров договоров и названием компании. Наши реквизиты указаны на сайте. Ваша учётная запись на форуме заблокирована за неуважительное поведение.
Официальная техподдержка. Официальная база знаний.
RSS Лента  Atom Лента
Пользователи, просматривающие эту тему
Быстрый переход  
Вы не можете создавать новые темы в этом форуме.
Вы не можете отвечать в этом форуме.
Вы не можете удалять Ваши сообщения в этом форуме.
Вы не можете редактировать Ваши сообщения в этом форуме.
Вы не можете создавать опросы в этом форуме.
Вы не можете голосовать в этом форуме.