我正在尝试使用OpenSSL从c程序计算sha1哈希值。我正在使用Intel i7(64位)在Mac OS X Yosemite上编译clang。
相关的代码大致如此:
#include <openssl/evp.h>
...
unsigned char outHash[20];
hash("SHA1","abcd", 20, outHash);
问题是,当使用openssl/evp.h
中的“哈希”函数时,使用clang进行编译会产生以下错误:
Undefined symbols for architecture x86_64:
"_hash", referenced from:
_getRandomSHA1 in main-68ccd6.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
因此看起来连接器找不到OpenSSL(“哈希”功能未被识别)。有想法该怎么解决这个吗?
修改
事实证明我试图使用一个不存在的函数(“hash”) - 抱歉误导了你。
但是我仍然遇到了同样的问题:包括openssl/evp.h
似乎不起作用。
这是我正在使用的哈希函数,它使用evp来执行sha1编码:
unsigned int hash(const char *mode, const char* dataToHash, size_t dataSize, unsigned char* outHashed) {
unsigned int md_len = -1;
const EVP_MD *md = EVP_get_digestbyname(mode);
if(NULL != md) {
EVP_MD_CTX mdctx;
EVP_MD_CTX_init(&mdctx);
EVP_DigestInit_ex(&mdctx, md, NULL);
EVP_DigestUpdate(&mdctx, dataToHash, dataSize);
EVP_DigestFinal_ex(&mdctx, outHashed, &md_len);
EVP_MD_CTX_cleanup(&mdctx);
}
return md_len;
}
然后我打电话给:
hash("SHA1","abcd", 20, outHash);
我和以前一样编译,这是我的编译命令(非常简单):
clang main.c
我从链接器收到以下错误:
Undefined symbols for architecture x86_64:
"_EVP_DigestFinal_ex", referenced from:
_hash in main-935849.o
"_EVP_DigestInit_ex", referenced from:
_hash in main-935849.o
"_EVP_DigestUpdate", referenced from:
_hash in main-935849.o
"_EVP_MD_CTX_cleanup", referenced from:
_hash in main-935849.o
"_EVP_MD_CTX_init", referenced from:
_hash in main-935849.o
"_EVP_get_digestbyname", referenced from:
_hash in main-935849.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
答案 0 :(得分:4)
#include <openssl/evp.h> ... unsigned char outHash[20]; hash("SHA1","abcd", 20, outHash);
OpenSSL没有int hash(...)
或char* hash(...)
功能。
$ cat /usr/include/openssl/evp.h | grep hash
返回0次点击。 man 3 hash
返回BSD的“哈希数据库访问方法”。
Undefined symbols for architecture x86_64: "_hash", referenced from: _getRandomSHA1 in main-68ccd6.o
锁定到_getRandomSHA1
,有一个SHA
功能,但可以从sha.h
获取,而不是evp.h
(我过滤了DEPRECTAED_IN...
宏):
$ cat /usr/include/openssl/sha.h | grep SHA | grep char
...
unsigned char *SHA(const unsigned char *d, size_t n, unsigned char *md);
...
我认为它使用静态缓冲区,不鼓励使用它。
项目建议现在使用EVP Message Digests界面。
( EDIT ):我和以前一样编译,这是我的编译命令 (很简单):
clang main.c
见Linking OpenSSL libraries to a program。您需要将 -lcrypto
添加到编译命令的 end 。
(编辑,来自评论):我在/ opt / local / include / openssl上有openssl ....
您将遇到更多问题,因为您可能正在运行时链接到错误的版本的OpenSSL库。对于该问题,请参阅Statically link OpenSSL in XCode。命令行和Xcode存在同样的问题。
这是最简单的解决方案。请注意, 不 使用-lcrypto
(-lfoo
通常是解决方案,除非运行时链接到错误的共享对象成为问题):
clang main.c -I /opt/local/include /opt/local/lib/libcrypto.a -o my_hash.exe
存档只是目标文件的集合,因此可以在需要目标文件的位置使用存档。
OX S不尊重RPATHs
另一个解决方案是使用。RPATH
构建OpenSSL和您的程序,以便在运行时加载正确的库版本。为此,请参阅OpenSSL wiki上的Compilation and Installation | Using RPATHs和Stack Overflow上的Build OpenSSL with RPATH?。
答案 1 :(得分:1)
您使用的是哪个SDK,以及哪个版本的Xcode? OpenSSL在OS X 10.7中已被弃用,并从10.11 SDK中删除,后者随Xcode 7 Beta一起提供。单独下载OpenSSL应该可以工作,但您可能需要更改新位置的项目配置。