2010-11-10 1 views
6

Где я могу найти простой пример кода для шифрования и дешифрования с открытым ключом в Mac OS X? Я расстроен тем, что в «Руководстве по программированию сертификатов, ключей и доверительных сервисов Apple» показано, как это сделать на iOS, но необходимые API-интерфейсы (SecKeyEncrypt, SecKeyDecrypt), по-видимому, недоступны в Mac OS X. Возможно, есть способ сделать это в «CryptoSample», но это не выглядит ясным или простым, и примерный проект слишком стар, чтобы открыть текущую версию Xcode.Пример кода для шифрования/дешифрования открытого ключа на Mac?

ответ

6

API-интерфейсы Security Framework довольно часто меняются между выпусками Mac OS. Лучший подход зависит от того, какую версию вы предназначаться:

  1. Если ваш код нужен только для запуска на 10.7 и выше, вы можете использовать Security, трансформаций нового высокого уровня общественного API для криптографических преобразований. Security Трансформации Руководство Программирование имеет полезный (и просто!) Пример кода:

    http://developer.apple.com/library/mac/#documentation/Security/Conceptual/SecTransformPG/SecurityTransformsBasics/SecurityTransformsBasics.html

    Вы хотите создать преобразование с помощью SecEncryptTransformCreate или SecDecryptTransformCreate, установите его ввода с помощью SecTransformSetAttribute и выполнить его с SecTransformExecute.

  2. Если вам необходимо поддерживать Mac OS 10.6 или ниже, вы должны использовать низкоуровневые и довольно страшные API-интерфейсы CDSA. CryptoSample - cdsaEncrypt - это краткий пример.

    http://developer.apple.com/library/mac/#samplecode/CryptoSample/Listings/libCdsaCrypt_libCdsaCrypt_cpp.html

    Вы можете получить CSSM_CSP_HANDLE и CSSM_KEY из SecKeyRef с помощью SecKeyGetCSPHandle и SecKeyGetCSSMKey соответственно.

    Чтобы узнать больше о ЦДСА, полная спецификация доступна от Open Group (бесплатно, но требует регистрации):

    https://www2.opengroup.org/ogsys/jsp/publications/PublicationDetails.jsp?publicationid=11287

    Успехов!

  3. Если закрытый ключ был создан для экспорта, вы можете экспортировать его в незащищенный формат и напрямую использовать openssl. Это ставит необработанные ключевые данные непосредственно в адресное пространство вашего приложения, поэтому оно побеждает одну из основных целей Keychain. Не делай этого.

  4. Наконец, вы можете общаться с частными функциями. Mac OS 10.6 и 10.7 включают, но не публично объявляют, SecKeyEncrypt и SecKeyDecrypt, с теми же аргументами, что и на iOS. Быстрое «грязное» решение состоит в том, чтобы просто объявить и использовать их (слабосвязанные, с обычными оговорками). Вероятно, это плохая идея сделать в коде, который вы планируете распространять другим.

+0

Согласно документации, Transforms безопасности не может использовать RSA-ключ, а OpenSSL устарел для использования в сторонних приложениях. Так что только # 2 и # 4 реалистичны. Я не могу себе представить, почему Apple не сделала публичный API SecKeyEncrypt и SecKeyDecrypt в OS X. Они не могут реально избежать их поддержки (навсегда и никогда), не нарушая имитатор iOS, а SDK iOS перечисляет их как доступные в OS X. Кто-то, вероятно, поместил #if в неподходящее место, и его неправильно разделили из заголовков. Пожалуйста, укажите ошибку. – dgatwood

1

Mac OS X содержит OpenSSL в libcrypto. Структура CommonCrypto, по-видимому, получена из SSLeay, предшественника OpenSSL.

+0

Я не сомневаюсь, что Mac OS X имеет API, который может это сделать, но вопрос был о «простом образце кода». – JWWalker

+0

Apple * сильно * препятствует использованию openssl на Mac. Аргумент со стороны Apple - это не столь стабильный API для openssl. Использование Security.framework - рекомендуемый API в Mac OS X. – Trenskow

4

Существует реализация расшифровки данных с использованием открытого ключа по адресу: https://github.com/karstenBriksoft/CSSMPublicKeyDecrypt. В Security.framework нет общедоступного API для такого рода функциональных возможностей, поэтому CSSM необходимо использовать напрямую, даже если его отмеченные как устаревшие. Для шифрования открытым ключом просто используйте SecEncryptTransformCreate, но для расшифровки с открытым ключом вам необходимо использовать класс CSSMPublicKeyDecrypt.

+0

Разве вы не должны использовать закрытый ключ для дешифрования? –

+1

Он может идти в обоих направлениях. Шифрование с помощью секретного ключа и дешифрование с помощью открытого ключа - это цифровое подписание (см. Http://en.wikipedia.org/wiki/Public-key_cryptography#Inverse_Public_Key_Encryption). – Karsten