universal8895: set blk loop min to 16
[GitHub/exynos8895/android_kernel_samsung_universal8895.git] / scripts / fips_fmp_utils.c
CommitLineData
1cac41cb
MB
1/*
2 * Utility functions called from fips_fmp_hmac.sh.
3 *
4 * executed during Kernel build
5 *
6 * Copyright (c) 2014 Samsung Electronics
7 *
8 */
9
10#include <stdio.h>
11#include <stdlib.h>
12#include <string.h>
13
14#define MAX_SIZE 0x100000
15
16int update_fmp_hmac(const char *vmlinux_path, const char *hmac_path, unsigned long offset);
17int collect_fmp_bytes(const char *in_file, const char *section_name, unsigned long offset,
18 unsigned long size, const char *out_file);
19
20int main(int argc, char **argv)
21{
22 if (argc < 2) {
23 printf("\nUsage : \n");
24 printf("fips_fmp_utils -u vmlinux_file hmac_file offset");
25 printf("fips_fmp_utils -g vmlinux_file section_name offset size out_file");
26 printf("\n");
27
28 return -1;
29 }
30
31 if (!strncmp("-u", argv[1], sizeof("-u"))) {
32 unsigned long offset = 0;
33 unsigned char *vmlinux_file = NULL;
34 unsigned char *hmac_file = NULL;
35
36 if (argc != 5) {
37 printf("\nUsage : \n");
38 printf("fips_fmp_utils -u vmlinux_file hmac_file offset");
39 printf("\n");
40
41 return -1;
42 }
43
44 vmlinux_file = argv[2];
45 hmac_file = argv[3];
46 offset = atol(argv[4]);
47
48 if (!vmlinux_file || !hmac_file || !offset) {
49 printf ("./fips_fmp_utils -u vmlinux_file hmac_file offset");
50 return -1;
51 }
52
53 return update_fmp_hmac(vmlinux_file, hmac_file, offset);
54 } else if (!strncmp("-g", argv[1], sizeof("-g"))) {
55 const char *in_file = NULL;
56 const char *section_name = NULL;
57 unsigned long offset = 0;
58 unsigned long size = 0;
59 const char *out_file = NULL;
60
61 if (argc != 7) {
62 printf("\nUsage : \n");
63 printf("./fips_fmp_utils -g vmlinux_file section_name offset size out_file");
64 printf("\n");
65
66 return -1;
67 }
68
69 in_file = argv[2];
70 section_name = argv[3];
71 offset = atol(argv[4]);
72 size = atol(argv[5]);
73 out_file = argv[6];
74
75 if (!in_file || !section_name || !offset || !size || !out_file) {
76 printf("./fips_fmp_utils -g vmlinux_file section_name offset size out_file");
77 return -1;
78 }
79
80 if (size > MAX_SIZE) {
81 printf("Fail fips_fmp_utils due to invalid size: %ld\n", size);
82 return -1;
83 }
84
85 return collect_fmp_bytes(in_file, section_name, offset, size, out_file);
86 } else {
87 printf("\nUsage : \n");
88 printf("fips_fmp_utils -u vmlinux_file hmac_file offset");
89 printf("fips_fmp_utils -g vmlinux_file section_name offset size out_file");
90 printf("\n");
91 }
92
93 return -1;
94}
95
96/*
97 * Given a vmlinux file, dumps "size" bytes from given "offset" to output file
98 * in_file : absolute path to vmlinux file
99 * section_name : Used only for printing / debugging
100 * offset : offset in file from where to dump bytes
101 * size : how many bytes to dump
102 * out_file : Output file, where to dump bytes.
103 * Open in append mode, to keep previous bytes, if present
104 * Caller need to clean up before 1st call
105 *
106 * Returns 0, if success
107 * -1, if error
108 */
109
110int collect_fmp_bytes(const char *in_file, const char *section_name, unsigned long offset,
111 unsigned long size, const char *out_file)
112{
113 FILE *in_fp = NULL;
114 FILE *out_fp = NULL;
115 unsigned int i = 0;
116 unsigned char data = 0;
117
118 if (!in_file || !section_name || !offset || !size || !out_file) {
119 printf ("collect_fmp_bytes : Invalid arguments");
120 return -1;
121 }
122
123 printf("Section : %s\n", section_name);
124
125 in_fp = fopen(in_file, "r");
126 if (!in_fp) {
127 printf("Unable to open file : %s", in_file);
128 return -1;
129 }
130
131 if (fseek(in_fp, offset, SEEK_SET) != 0) {
132 printf ("Unable to seek file : %s", in_file);
133 goto err_fseek;
134 }
135
136 out_fp = fopen(out_file, "ab");
137 if (!out_fp) {
138 printf ("Unable to open file : %s", out_file);
139 goto err_open_out_fp;
140 }
141
142 if (size > MAX_SIZE) {
143 printf("Fail fips_fmp_utils due to invalid size: %ld\n", size);
144 goto err;
145 }
146
147 if (size > MAX_SIZE) {
148 printf("Fail fips_fmp_utils due to invalid size: %ld\n", size);
149 return -1;
150 }
151
152 for (i = 1; i <= size; i++) {
153 if ( 1 != fread (&data, sizeof(unsigned char), 1, in_fp)) {
154 printf("Unable to read 1 byte from file : %s", in_file);
155 goto err;
156 }
157
158 printf ("%02x ", data);
159 if (1 != fwrite (&data, 1, 1, out_fp)) {
160 printf("Unable to write 1 byte to file : %s", out_file);
161 goto err;
162 }
163
164 if (!(i % 16))
165 printf("\n");
166 }
167
168 fclose(out_fp);
169 fclose(in_fp);
170
171 return 0;
172err:
173 fclose(out_fp);
174err_open_out_fp:
175err_fseek:
176 fclose(in_fp);
177 return -1;
178}
179
180#define SHA256_DIGEST_SIZE 32
181
182/*
183 * Given a vmlinux file, overwrites bytes at given offset with hmac bytes, available in
184 * hmac file.
185 * Return 0, if Success
186 * -1, if Error
187 */
188int update_fmp_hmac(const char *vmlinux_path, const char *hmac_path, unsigned long offset)
189{
190 FILE *vmlinux_fp = NULL;
191 FILE *hmac_fp = NULL;
192 int i = 0, j = 0;
193 unsigned char hmac[SHA256_DIGEST_SIZE];
194
195 if (!vmlinux_path || !hmac_path || !offset) {
196 printf("FIPS update_fmp_hmac : Invalid Params");
197 return -1;
198 }
199
200 vmlinux_fp = fopen(vmlinux_path, "r+b");
201 if (!vmlinux_fp) {
202 printf("Unable to open vmlinux file ");
203 return -1;
204 }
205
206 hmac_fp = fopen(hmac_path, "rb");
207 if (!hmac_fp) {
208 printf("Unable to open hmac file ");
209 goto err_open_hmac_fp;
210 }
211
212 if (SHA256_DIGEST_SIZE != fread(&hmac, sizeof(unsigned char), SHA256_DIGEST_SIZE, hmac_fp)) {
213 printf("Unable to read %d bytes from hmac file", SHA256_DIGEST_SIZE);
214 goto err;
215 }
216
217 if (fseek(vmlinux_fp, offset, SEEK_SET) != 0) {
218 printf("Unable to seek into vmlinux file.");
219 goto err;
220 }
221
222 if (SHA256_DIGEST_SIZE != fwrite (hmac, sizeof(unsigned char), SHA256_DIGEST_SIZE, vmlinux_fp)) {
223 printf("Unable to write %d byte into vmlinux", SHA256_DIGEST_SIZE);
224 goto err;
225 }
226
227 fclose(vmlinux_fp);
228 fclose(hmac_fp);
229
230 return 0;
231
232err:
233 fclose(hmac_fp);
234err_open_hmac_fp:
235 fclose(vmlinux_fp);
236 return -1;
237}