xref: /aosp_15_r20/external/vboot_reference/host/lib21/host_misc.c (revision 8617a60d3594060b7ecbd21bc622a7c14f3cf2bc)
1*8617a60dSAndroid Build Coastguard Worker /* Copyright 2014 The ChromiumOS Authors
2*8617a60dSAndroid Build Coastguard Worker  * Use of this source code is governed by a BSD-style license that can be
3*8617a60dSAndroid Build Coastguard Worker  * found in the LICENSE file.
4*8617a60dSAndroid Build Coastguard Worker  *
5*8617a60dSAndroid Build Coastguard Worker  * Host functions for verified boot.
6*8617a60dSAndroid Build Coastguard Worker  */
7*8617a60dSAndroid Build Coastguard Worker 
8*8617a60dSAndroid Build Coastguard Worker #include <ctype.h>
9*8617a60dSAndroid Build Coastguard Worker #include <stdio.h>
10*8617a60dSAndroid Build Coastguard Worker #include <string.h>
11*8617a60dSAndroid Build Coastguard Worker #include <unistd.h>
12*8617a60dSAndroid Build Coastguard Worker 
13*8617a60dSAndroid Build Coastguard Worker #include "2common.h"
14*8617a60dSAndroid Build Coastguard Worker #include "2sha.h"
15*8617a60dSAndroid Build Coastguard Worker #include "2sysincludes.h"
16*8617a60dSAndroid Build Coastguard Worker #include "host_common.h"
17*8617a60dSAndroid Build Coastguard Worker #include "host_common21.h"
18*8617a60dSAndroid Build Coastguard Worker #include "host_misc21.h"
19*8617a60dSAndroid Build Coastguard Worker 
vb2_read_file(const char * filename,uint8_t ** data_ptr,uint32_t * size_ptr)20*8617a60dSAndroid Build Coastguard Worker vb2_error_t vb2_read_file(const char *filename, uint8_t **data_ptr,
21*8617a60dSAndroid Build Coastguard Worker 			  uint32_t *size_ptr)
22*8617a60dSAndroid Build Coastguard Worker {
23*8617a60dSAndroid Build Coastguard Worker 	FILE *f;
24*8617a60dSAndroid Build Coastguard Worker 	uint8_t *buf;
25*8617a60dSAndroid Build Coastguard Worker 	long size;
26*8617a60dSAndroid Build Coastguard Worker 
27*8617a60dSAndroid Build Coastguard Worker 	*data_ptr = NULL;
28*8617a60dSAndroid Build Coastguard Worker 	*size_ptr = 0;
29*8617a60dSAndroid Build Coastguard Worker 
30*8617a60dSAndroid Build Coastguard Worker 	f = fopen(filename, "rb");
31*8617a60dSAndroid Build Coastguard Worker 	if (!f) {
32*8617a60dSAndroid Build Coastguard Worker 		VB2_DEBUG("Unable to open file %s\n", filename);
33*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_READ_FILE_OPEN;
34*8617a60dSAndroid Build Coastguard Worker 	}
35*8617a60dSAndroid Build Coastguard Worker 
36*8617a60dSAndroid Build Coastguard Worker 	fseek(f, 0, SEEK_END);
37*8617a60dSAndroid Build Coastguard Worker 	size = ftell(f);
38*8617a60dSAndroid Build Coastguard Worker 	rewind(f);
39*8617a60dSAndroid Build Coastguard Worker 
40*8617a60dSAndroid Build Coastguard Worker 	if (size < 0 || size > UINT32_MAX) {
41*8617a60dSAndroid Build Coastguard Worker 		fclose(f);
42*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_READ_FILE_SIZE;
43*8617a60dSAndroid Build Coastguard Worker 	}
44*8617a60dSAndroid Build Coastguard Worker 
45*8617a60dSAndroid Build Coastguard Worker 	buf = malloc(size + 1);
46*8617a60dSAndroid Build Coastguard Worker 	if (!buf) {
47*8617a60dSAndroid Build Coastguard Worker 		fclose(f);
48*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_READ_FILE_ALLOC;
49*8617a60dSAndroid Build Coastguard Worker 	}
50*8617a60dSAndroid Build Coastguard Worker 	buf[size] = '\0';
51*8617a60dSAndroid Build Coastguard Worker 
52*8617a60dSAndroid Build Coastguard Worker 	if (1 != fread(buf, size, 1, f)) {
53*8617a60dSAndroid Build Coastguard Worker 		VB2_DEBUG("Unable to read file %s\n", filename);
54*8617a60dSAndroid Build Coastguard Worker 		fclose(f);
55*8617a60dSAndroid Build Coastguard Worker 		free(buf);
56*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_READ_FILE_DATA;
57*8617a60dSAndroid Build Coastguard Worker 	}
58*8617a60dSAndroid Build Coastguard Worker 
59*8617a60dSAndroid Build Coastguard Worker 	fclose(f);
60*8617a60dSAndroid Build Coastguard Worker 
61*8617a60dSAndroid Build Coastguard Worker 	*data_ptr = buf;
62*8617a60dSAndroid Build Coastguard Worker 	*size_ptr = size;
63*8617a60dSAndroid Build Coastguard Worker 	return VB2_SUCCESS;
64*8617a60dSAndroid Build Coastguard Worker }
65*8617a60dSAndroid Build Coastguard Worker 
vb2_write_file(const char * filename,const void * buf,uint32_t size)66*8617a60dSAndroid Build Coastguard Worker vb2_error_t vb2_write_file(const char *filename, const void *buf, uint32_t size)
67*8617a60dSAndroid Build Coastguard Worker {
68*8617a60dSAndroid Build Coastguard Worker 	FILE *f = fopen(filename, "wb");
69*8617a60dSAndroid Build Coastguard Worker 
70*8617a60dSAndroid Build Coastguard Worker 	if (!f) {
71*8617a60dSAndroid Build Coastguard Worker 		VB2_DEBUG("Unable to open file %s\n", filename);
72*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_WRITE_FILE_OPEN;
73*8617a60dSAndroid Build Coastguard Worker 	}
74*8617a60dSAndroid Build Coastguard Worker 
75*8617a60dSAndroid Build Coastguard Worker 	if (1 != fwrite(buf, size, 1, f)) {
76*8617a60dSAndroid Build Coastguard Worker 		VB2_DEBUG("Unable to write to file %s\n", filename);
77*8617a60dSAndroid Build Coastguard Worker 		fclose(f);
78*8617a60dSAndroid Build Coastguard Worker 		unlink(filename);  /* Delete any partial file */
79*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_WRITE_FILE_DATA;
80*8617a60dSAndroid Build Coastguard Worker 	}
81*8617a60dSAndroid Build Coastguard Worker 
82*8617a60dSAndroid Build Coastguard Worker 	fclose(f);
83*8617a60dSAndroid Build Coastguard Worker 	return VB2_SUCCESS;
84*8617a60dSAndroid Build Coastguard Worker }
85*8617a60dSAndroid Build Coastguard Worker 
vb21_write_object(const char * filename,const void * buf)86*8617a60dSAndroid Build Coastguard Worker vb2_error_t vb21_write_object(const char *filename, const void *buf)
87*8617a60dSAndroid Build Coastguard Worker {
88*8617a60dSAndroid Build Coastguard Worker 	const struct vb21_struct_common *cptr = buf;
89*8617a60dSAndroid Build Coastguard Worker 
90*8617a60dSAndroid Build Coastguard Worker 	return vb2_write_file(filename, buf, cptr->total_size);
91*8617a60dSAndroid Build Coastguard Worker }
92*8617a60dSAndroid Build Coastguard Worker 
vb2_desc_size(const char * desc)93*8617a60dSAndroid Build Coastguard Worker uint32_t vb2_desc_size(const char *desc)
94*8617a60dSAndroid Build Coastguard Worker {
95*8617a60dSAndroid Build Coastguard Worker 	if (!desc || !*desc)
96*8617a60dSAndroid Build Coastguard Worker 		return 0;
97*8617a60dSAndroid Build Coastguard Worker 
98*8617a60dSAndroid Build Coastguard Worker 	return roundup32(strlen(desc) + 1);
99*8617a60dSAndroid Build Coastguard Worker }
100*8617a60dSAndroid Build Coastguard Worker 
onedigit(const char * str,uint8_t * vptr)101*8617a60dSAndroid Build Coastguard Worker static const char *onedigit(const char *str, uint8_t *vptr)
102*8617a60dSAndroid Build Coastguard Worker {
103*8617a60dSAndroid Build Coastguard Worker 	uint8_t val = 0;
104*8617a60dSAndroid Build Coastguard Worker 	char c;
105*8617a60dSAndroid Build Coastguard Worker 
106*8617a60dSAndroid Build Coastguard Worker 	for (; (c = *str++) && !isxdigit(c);)
107*8617a60dSAndroid Build Coastguard Worker 		;
108*8617a60dSAndroid Build Coastguard Worker 	if (!c)
109*8617a60dSAndroid Build Coastguard Worker 		return 0;
110*8617a60dSAndroid Build Coastguard Worker 
111*8617a60dSAndroid Build Coastguard Worker 	if (c >= '0' && c <= '9')
112*8617a60dSAndroid Build Coastguard Worker 		val = c - '0';
113*8617a60dSAndroid Build Coastguard Worker 	else if (c >= 'A' && c <= 'F')
114*8617a60dSAndroid Build Coastguard Worker 		val = 10 + c - 'A';
115*8617a60dSAndroid Build Coastguard Worker 	else if (c >= 'a' && c <= 'f')
116*8617a60dSAndroid Build Coastguard Worker 		val = 10 + c - 'a';
117*8617a60dSAndroid Build Coastguard Worker 
118*8617a60dSAndroid Build Coastguard Worker 	*vptr = val;
119*8617a60dSAndroid Build Coastguard Worker 	return str;
120*8617a60dSAndroid Build Coastguard Worker }
121*8617a60dSAndroid Build Coastguard Worker 
onebyte(const char * str,uint8_t * vptr)122*8617a60dSAndroid Build Coastguard Worker static const char *onebyte(const char *str, uint8_t *vptr)
123*8617a60dSAndroid Build Coastguard Worker {
124*8617a60dSAndroid Build Coastguard Worker 	uint8_t val;
125*8617a60dSAndroid Build Coastguard Worker 	uint8_t digit;
126*8617a60dSAndroid Build Coastguard Worker 
127*8617a60dSAndroid Build Coastguard Worker 	str = onedigit(str, &digit);
128*8617a60dSAndroid Build Coastguard Worker 	if (!str)
129*8617a60dSAndroid Build Coastguard Worker 		return 0;
130*8617a60dSAndroid Build Coastguard Worker 	val = digit << 4;
131*8617a60dSAndroid Build Coastguard Worker 
132*8617a60dSAndroid Build Coastguard Worker 	str = onedigit(str, &digit);
133*8617a60dSAndroid Build Coastguard Worker 	if (!str)
134*8617a60dSAndroid Build Coastguard Worker 		return 0;
135*8617a60dSAndroid Build Coastguard Worker 	val |= digit;
136*8617a60dSAndroid Build Coastguard Worker 
137*8617a60dSAndroid Build Coastguard Worker 	*vptr = val;
138*8617a60dSAndroid Build Coastguard Worker 	return str;
139*8617a60dSAndroid Build Coastguard Worker }
140*8617a60dSAndroid Build Coastguard Worker 
vb2_str_to_id(const char * str,struct vb2_id * id)141*8617a60dSAndroid Build Coastguard Worker vb2_error_t vb2_str_to_id(const char *str, struct vb2_id *id)
142*8617a60dSAndroid Build Coastguard Worker {
143*8617a60dSAndroid Build Coastguard Worker 	uint8_t val = 0;
144*8617a60dSAndroid Build Coastguard Worker 	int i;
145*8617a60dSAndroid Build Coastguard Worker 
146*8617a60dSAndroid Build Coastguard Worker 	if (!str)
147*8617a60dSAndroid Build Coastguard Worker 		return VB2_ERROR_STR_TO_ID;
148*8617a60dSAndroid Build Coastguard Worker 
149*8617a60dSAndroid Build Coastguard Worker 	memset(id, 0, sizeof(*id));
150*8617a60dSAndroid Build Coastguard Worker 
151*8617a60dSAndroid Build Coastguard Worker 	for (i = 0; i < VB2_ID_NUM_BYTES; i++) {
152*8617a60dSAndroid Build Coastguard Worker 
153*8617a60dSAndroid Build Coastguard Worker 		str = onebyte(str, &val);
154*8617a60dSAndroid Build Coastguard Worker 		if (!str)
155*8617a60dSAndroid Build Coastguard Worker 			break;
156*8617a60dSAndroid Build Coastguard Worker 		id->raw[i] = val;
157*8617a60dSAndroid Build Coastguard Worker 	}
158*8617a60dSAndroid Build Coastguard Worker 
159*8617a60dSAndroid Build Coastguard Worker 	/* If we get at least one valid byte, that's good enough. */
160*8617a60dSAndroid Build Coastguard Worker 	return i ? VB2_SUCCESS : VB2_ERROR_STR_TO_ID;
161*8617a60dSAndroid Build Coastguard Worker }
162