Skip to content

Commit a101978

Browse files
committed
main program finished
1 parent 685cfa3 commit a101978

File tree

1 file changed

+285
-0
lines changed

1 file changed

+285
-0
lines changed

main.c

+285
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,285 @@
1+
#include <stdio.h>
2+
#include <stdlib.h>
3+
#include <string.h>
4+
#include <unistd.h>
5+
#include <stdbool.h>
6+
#include <inttypes.h>
7+
#include "srix.h"
8+
9+
10+
/**
11+
* Print help message.
12+
* @param executable name of executable
13+
*/
14+
static void printUsage(const char *executable) {
15+
printf("Usage: %s [-h] [-p] [-r file] [-w file] [-c] [-o]\n\n", executable);
16+
printf("Options:\n");
17+
printf(" -h show this help message\n");
18+
printf(" -p print information about NFC tag\n");
19+
printf(" -r file read eeprom from a file, if not present read from NFC tag\n");
20+
printf(" -w file write eeprom to a file\n");
21+
printf(" -c write changes to NFC tag eeprom\n");
22+
printf(" -o reset SRIX4K OTP blocks\n");
23+
}
24+
25+
26+
/**
27+
* Initialize srix from NFC.
28+
* @param srix struct to initialize
29+
* @return boolean result
30+
*/
31+
static bool readFromNfc(Srix *srix) {
32+
/* Get readers number */
33+
size_t readersNumber = NfcGetReadersCount(srix);
34+
35+
/* Exit if no readers available */
36+
if (readersNumber == 0) {
37+
fprintf(stderr, "Unable to find an NFC reader\n");
38+
return false;
39+
}
40+
41+
/* Print all readers */
42+
printf("Readers:\n");
43+
for (size_t i = 0; i < readersNumber; i++) {
44+
printf("[%" PRIu8 "] -> %s\n", (uint8_t) i, NfcGetDescription(srix, (int) i));
45+
}
46+
47+
/* Reader selector */
48+
uint8_t targetReader = 0;
49+
if (readersNumber > 1) {
50+
printf("Found %zu readers available\n", readersNumber);
51+
52+
/* Retry while input is out of range */
53+
do {
54+
printf("Insert the target reader [0-%zu]: ", readersNumber - 1);
55+
/* While input is invalid, clean input and retry */
56+
char buffer[8];
57+
fgets(buffer, sizeof(buffer), stdin);
58+
targetReader = strtol(buffer, (void *) 0, 10);
59+
} while (targetReader >= readersNumber);
60+
}
61+
62+
/* Init nfc */
63+
if (!SrixNfcInit(srix, targetReader)) {
64+
/* If result is null, print error */
65+
fprintf(stderr, "Selected reader is invalid\n");
66+
return false;
67+
}
68+
69+
return true;
70+
}
71+
72+
73+
/**
74+
* Initialize srix from a file.
75+
* @param srix struct to initialize
76+
* @param filename name of file
77+
* @return boolean result
78+
*/
79+
static bool readFromFile(Srix *srix, char *filename) {
80+
FILE *eeprom = fopen(filename, "r");
81+
if (!eeprom) {
82+
fprintf(stderr, "Unable to read input file\n");
83+
return false;
84+
}
85+
86+
// Read blocks
87+
uint32_t blocks[SRIX4K_BLOCKS];
88+
for (int i = 0; i < SRIX4K_BLOCKS; i++) {
89+
uint8_t buffer[SRIX_BLOCK_LENGTH];
90+
if (fread(buffer, sizeof(uint8_t), SRIX_BLOCK_LENGTH, eeprom) != SRIX_BLOCK_LENGTH) {
91+
fprintf(stderr, "Incorrect read value from input file\n");
92+
fclose(eeprom);
93+
return false;
94+
}
95+
96+
blocks[i] = buffer[0] << 24 | buffer[1] << 16 | buffer[2] << 8 | buffer[3];
97+
}
98+
99+
// Read UID
100+
uint8_t uidBytes[SRIX_UID_LENGTH];
101+
if (fread(uidBytes, sizeof(uint8_t), SRIX_UID_LENGTH, eeprom) != SRIX_UID_LENGTH) {
102+
fprintf(stderr, "Incorrect read value from input file\n");
103+
fclose(eeprom);
104+
return false;
105+
}
106+
107+
uint64_t uid = (uint64_t) uidBytes[7] << 56U | (uint64_t) uidBytes[6] << 48U | (uint64_t) uidBytes[5] << 40U |
108+
(uint64_t) uidBytes[4] << 32U | (uint64_t) uidBytes[3] << 24U | (uint64_t) uidBytes[2] << 16U |
109+
(uint64_t) uidBytes[1] << 8U | (uint64_t) uidBytes[0];
110+
111+
/* Save data to SRIX struct */
112+
SrixMemoryInit(srix, blocks, uid);
113+
fclose(eeprom);
114+
return true;
115+
}
116+
117+
118+
/**
119+
* Save data to a file.
120+
* @param srix struct to save
121+
* @param filename name of file
122+
* @return boolean result
123+
*/
124+
static bool writeToFile(Srix *srix, char *filename) {
125+
FILE *outputFile = fopen(filename, "w");
126+
if (!outputFile) {
127+
fprintf(stderr, "Unable to open output file\n");
128+
return false;
129+
}
130+
131+
// Write blocks
132+
for (int i = 0; i < SRIX4K_BLOCKS; i++) {
133+
uint32_t block = *SrixGetBlock(srix, i);
134+
uint8_t buffer[SRIX_BLOCK_LENGTH] = {block >> 24, block >> 16, block >> 8, block};
135+
136+
if (fwrite(buffer, sizeof(uint8_t), SRIX_BLOCK_LENGTH, outputFile) != SRIX_BLOCK_LENGTH) {
137+
fprintf(stderr, "Incorrect written value to output file\n");
138+
fclose(outputFile);
139+
return false;
140+
}
141+
}
142+
143+
// Write UID
144+
uint64_t uid = SrixGetUid(srix);
145+
uint8_t uidBytes[SRIX_UID_LENGTH] = {uid, uid >> 8, uid >> 16, uid >> 24, uid >> 32,
146+
uid >> 40, uid >> 48, uid >> 56};
147+
if (fwrite(uidBytes, sizeof(uint8_t), SRIX_UID_LENGTH, outputFile) != SRIX_UID_LENGTH) {
148+
fprintf(stderr, "Incorrect written value to output file\n");
149+
fclose(outputFile);
150+
return false;
151+
}
152+
153+
fclose(outputFile);
154+
return true;
155+
}
156+
157+
int main(int argc, char *argv[]) {
158+
/* Check if there are arguments */
159+
if (argc == 1) {
160+
printUsage(argv[0]);
161+
return EXIT_FAILURE;
162+
}
163+
164+
bool printInformation = false;
165+
char *readFile = (void *) 0;
166+
char *writeFile = (void *) 0;
167+
bool writeTag = false;
168+
bool resetOTP = false;
169+
170+
/* Parse input arguments */
171+
int param;
172+
while ((param = getopt(argc, argv, "hpr:w:co")) != -1) {
173+
switch (param) {
174+
case 'h':
175+
printUsage(argv[0]);
176+
return EXIT_SUCCESS;
177+
case 'p':
178+
printInformation = true;
179+
break;
180+
case 'r':
181+
readFile = optarg;
182+
break;
183+
case 'w':
184+
writeFile = optarg;
185+
break;
186+
case 'c':
187+
writeTag = true;
188+
break;
189+
case 'o':
190+
resetOTP = true;
191+
break;
192+
default:
193+
printUsage(argv[0]);
194+
return EXIT_FAILURE;
195+
}
196+
}
197+
198+
Srix *srix = SrixNew();
199+
if (srix == (void *) 0) {
200+
fprintf(stderr, "Unable to allocate memory for SRIX\n");
201+
return EXIT_FAILURE;
202+
}
203+
204+
/* Initialize NFC if read tag or write tag is enabled */
205+
if (!readFile || writeTag) {
206+
if (!readFromNfc(srix)) {
207+
return EXIT_FAILURE;
208+
}
209+
}
210+
211+
/* Get data from file */
212+
if (readFile) {
213+
if (!readFromFile(srix, readFile)) {
214+
return EXIT_FAILURE;
215+
}
216+
}
217+
218+
/* Print information in stdout */
219+
if (printInformation) {
220+
printf("UID: %lu\n\n", SrixGetUid(srix));
221+
222+
printf("EEPROM:\n");
223+
for (int i = 0; i < SRIX4K_BLOCKS; i++) {
224+
printf("[%02X] -> %08X", i, *SrixGetBlock(srix, i));
225+
}
226+
}
227+
228+
/* Reset OTP blocks */
229+
if (resetOTP) {
230+
/* If at least one OTP block is different than
231+
* 0xFFFFFFFF, reset OTP.
232+
* OTP Blocks: 0x00, 0x01, 0x02, 0x03, 0x04
233+
*/
234+
bool toReset = false;
235+
for (int i = 0x00; i <= 0x04; i++) {
236+
if (*SrixGetBlock(srix, i) != 0xFFFFFFFF) {
237+
toReset = true;
238+
}
239+
}
240+
241+
if (toReset) {
242+
/* Decrease block 6 */
243+
uint32_t block6old = *SrixGetBlock(srix, 0x06);
244+
uint32_t block6 =
245+
(block6old << 24) | ((block6old & 0x0C) << 8) | ((block6old & 0x30) >> 8) | (block6old >> 24);
246+
247+
uint32_t toDecrease = 0x00200000;
248+
if (block6 < toDecrease) {
249+
fprintf(stderr, "Unable to decrease block6 counter");
250+
return EXIT_FAILURE;
251+
} else {
252+
/* If result will be higher than 0, subtract. */
253+
block6 -= toDecrease;
254+
}
255+
256+
block6 = (block6 << 24) | ((block6 & 0x0C) << 8) | ((block6 & 0x30) >> 8) | (block6 >> 24);
257+
258+
SrixModifyBlock(srix, block6, 0x06);
259+
SrixModifyBlock(srix, 0xFFFFFFFF, 0x00);
260+
SrixModifyBlock(srix, 0xFFFFFFFF, 0x01);
261+
SrixModifyBlock(srix, 0xFFFFFFFF, 0x02);
262+
SrixModifyBlock(srix, 0xFFFFFFFF, 0x03);
263+
SrixModifyBlock(srix, 0xFFFFFFFF, 0x04);
264+
}
265+
}
266+
267+
/* Write result to file */
268+
if (writeFile) {
269+
if (!writeToFile(srix, writeFile)) {
270+
return EXIT_FAILURE;
271+
}
272+
}
273+
274+
/* Write result to tag */
275+
if (writeTag) {
276+
if (SrixWriteBlocks(srix) != SRIX_SUCCESS) {
277+
fprintf(stderr, "Unable to write blocks to SRIX4K");
278+
}
279+
}
280+
281+
/* Delete srix at the end */
282+
SrixDelete(srix);
283+
284+
return EXIT_SUCCESS;
285+
}

0 commit comments

Comments
 (0)