最近游戏后台接入腾讯敏感词接口: /v3/user/uic_filter 需要加密方式是hmac_sha1,项目中没有,于是从网上找了库,最后上线应用。说下具体流程和注意的坑:
关键的函数:HMAC_SHA1
注意的点:mars_https::BYTE digest[20];这里数组一定要是20
最终要经过另一个函数调用洗礼:byteToHexStr
以下是测试代码和库函数。

1 #include <iostream>
2 #include <math.h>
3 #include "HmacSha1.h"
4 #include <string>
5 using namespace std;
6
7 string byteToHexStr(unsigned char byte_arr[], int arr_len)
8 {
9 string hexstr;
10 for (int i=0;i<arr_len;i++)
11 {
12 char hex1;
13 char hex2;
14 int value=byte_arr[i];
15 int v1=value/16;
16 int v2=value % 16;
17
18 //将商转成字母
19 if (v1>=0&&v1<=9)
20 hex1=(char)(48+v1);
21 else
22 hex1=(char)(55+v1);
23
24 //将余数转成字母
25 if (v2>=0&&v2<=9)
26 hex2=(char)(48+v2);
27 else
28 hex2=(char)(55+v2);
29
30 //将字母连接成串
31 hexstr=hexstr+hex1+hex2;
32 }
33 return hexstr;
34 }
35 int main()
36 {
37 string strJoin = "POST&%2Fv3%2Fuser%2Fuic_filter&appid%3D1105752926%26openid%3D33FA239D835DADB54CC6E06D100AB989%26openkey%3DAFE95D97DF01E8DC8F7C75E1041AD1E2";
38 string strKey = "0aYIIoABlh3VCM4I&";
39 mars_https::BYTE digest[20];
40 mars_https::HMAC_SHA1((mars_https::BYTE*)strJoin.c_str(), strlen(strJoin.c_str()),(mars_https::BYTE*)strKey.c_str(),strlen(strKey.c_str()),digest);
41 int len = sizeof(digest);
42 string m_strSerialNumber=byteToHexStr(digest,len).c_str();
43 cout<<m_strSerialNumber<<endl;
44 return 0;
45 }
Sha1.cpp

1 /*
2 100% free public domain implementation of the SHA-1 algorithm
3 by Dominik Reichl <dominik.reichl@t-online.de>
4 Web: http://www.dominik-reichl.de/
5
6 Version 1.6 - 2005-02-07 (thanks to Howard Kapustein for patches)
7 - You can set the endianness in your files, no need to modify the
8 header file of the CSHA1 class any more
9 - Aligned data support
10 - Made support/compilation of the utility functions (ReportHash
11 and HashFile) optional (useful, if bytes count, for example in
12 embedded environments)
13
14 Version 1.5 - 2005-01-01
15 - 64-bit compiler compatibility added
16 - Made variable wiping optional (define SHA1_WIPE_VARIABLES)
17 - Removed unnecessary variable initializations
18 - ROL32 improvement for the Microsoft compiler (using _rotl)
19
20 ======== Test Vectors (from FIPS PUB 180-1) ========
21
22 SHA1("abc") =
23 A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D
24
25 SHA1("abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq") =
26 84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1
27
28 SHA1(A million repetitions of "a") =
29 34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F
30 */
31
32 #ifndef ___SHA1_HDR___
33 #define ___SHA1_HDR___
34
35 #if !defined(SHA1_UTILITY_FUNCTIONS) && !defined(SHA1_NO_UTILITY_FUNCTIONS)
36 #define SHA1_UTILITY_FUNCTIONS
37 #endif
38
39 #include <memory.h> // Needed for memset and memcpy
40
41 #ifdef SHA1_UTILITY_FUNCTIONS
42 #include <stdio.h> // Needed for file access and sprintf
43 #include <string.h> // Needed for strcat and strcpy
44 #endif
45
46 #ifdef _MSC_VER
47 #include <stdlib.h>
48 #endif
49
50 // You can define the endian mode in your files, without modifying the SHA1
51 // source files. Just #define SHA1_LITTLE_ENDIAN or #define SHA1_BIG_ENDIAN
52 // in your files, before including the SHA1.h header file. If you don't
53 // define anything, the class defaults to little endian.
54
55 #if !defined(SHA1_LITTLE_ENDIAN) && !defined(SHA1_BIG_ENDIAN)
56 #define SHA1_LITTLE_ENDIAN
57 #endif
58
59 // Same here. If you want variable wiping, #define SHA1_WIPE_VARIABLES, if
60 // not, #define SHA1_NO_WIPE_VARIABLES. If you don't define anything, it
61 // defaults to wiping.
62
63 #if !defined(SHA1_WIPE_VARIABLES) && !defined(SHA1_NO_WIPE_VARIABLES)
64 #define SHA1_WIPE_VARIABLES
65 #endif
66
67 /////////////////////////////////////////////////////////////////////////////
68 // Define 8- and 32-bit variables
69
70 #ifndef UINT_32
71
72 #ifdef _MSC_VER
73
74 #define UINT_8 unsigned __int8
75 #define UINT_32 unsigned __int32
76
77 #else
78
79 #define UINT_8 unsigned char
80
81 #if (ULONG_MAX == 0xFFFFFFFF)
82 #define UINT_32 unsigned long
83 #else
84 #define UINT_32 unsigned int
85 #endif
86
87 #endif
88 #endif
89
90 /////////////////////////////////////////////////////////////////////////////
91 // Declare SHA1 workspace
92
93 typedef union
94 {
95 UINT_8 c[64];
96 UINT_32 l[16];
97 } SHA1_WORKSPACE_BLOCK;
98
99 class CSHA1
100 {
101 public:
102 #ifdef SHA1_UTILITY_FUNCTIONS
103 // Two different formats for ReportHash(...)
104 enum
105 {
106 REPORT_HEX = 0,
107 REPORT_DIGIT = 1
108 };
109 #endif
110
111 // Constructor and Destructor
112 CSHA1();
113 ~CSHA1();
114
115 UINT_32 m_state[5];
116 UINT_32 m_count[2];
117 UINT_32 __reserved1[1];
118 UINT_8 m_buffer[64];
119 UINT_8 m_digest[20];
120 UINT_32 __reserved2[3];
121
122 void Reset();
123
124 // Update the hash value
125 void Update(UINT_8 *data, UINT_32 len);
126 #ifdef SHA1_UTILITY_FUNCTIONS
127 bool HashFile(char *szFileName);
128 #endif
129
130 // Finalize hash and report
131 void Final();
132
133 // Report functions: as pre-formatted and raw data
134 #ifdef SHA1_UTILITY_FUNCTIONS
135 void ReportHash(char *szReport, unsigned char uReportType = REPORT_HEX);
136 #endif
137 void GetHash(UINT_8 *puDest);
138
139 private:
140 // Private SHA-1 transformation
141 void Transform(UINT_32 *state, UINT_8 *buffer);
142
143 // Member variables
144 UINT_8 m_workspace[64];
145 SHA1_WORKSPACE_BLOCK *m_block; // SHA1 pointer to the byte array above
146 };
147
148 #endif
HmacSha1.cpp
HmacSha1.h
若有问题希望留言指正,感谢~
来源:https://www.cnblogs.com/workharder/p/12190497.html
