Created
March 5, 2020 11:16
-
-
Save digetx/576a4ec9859e85e1beb8d03c1b97aa40 to your computer and use it in GitHub Desktop.
parse_tegrapt
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <stdio.h> | |
#include <stdlib.h> | |
#include <string.h> | |
#include <unistd.h> | |
#include <fcntl.h> | |
#include <errno.h> | |
#include <openssl/sha.h> | |
#include <stdbool.h> | |
#include <stdint-gcc.h> | |
#define _GNU_SOURCE | |
typedef struct NvFsMountInfoRec | |
{ | |
uint32_t DeviceId; // 4 | |
uint32_t DeviceInstance; // 4 | |
uint32_t DeviceAttr; // 4 | |
char MountPath[4]; // 4 | |
uint32_t FileSystemType; // 4 | |
uint32_t FileSystemAttr; // 4 | |
} NvFsMountInfo; | |
typedef struct NvPartInfoRec | |
{ | |
uint32_t PartitionAttr; // 4 4 | |
uint32_t Padding1; // 4 8 | |
uint64_t LogicalSectorAddress; // 8 16 | |
uint64_t NumLogicalSectors; // 8 24 | |
uint64_t StartPhysicalSectorAddress; // 8 32 | |
uint64_t EndPhysicalSectorAddress; // 8 40 | |
uint32_t PartitionType; // 4 44 | |
uint32_t Padding2; // 4 48 | |
} NvPartInfo; | |
typedef struct NvPartTableHeaderInsecureRec | |
{ | |
uint64_t Magic; | |
uint32_t InsecureVersion; | |
uint32_t InsecureLength; | |
uint8_t Signature[16]; | |
} NvPartTableHeaderInsecure; | |
typedef struct NvPartTableHeaderSecureRec | |
{ | |
uint8_t RandomData[16]; | |
uint64_t SecureMagic; | |
uint32_t SecureVersion; | |
uint32_t SecureLength; | |
uint32_t NumPartitions; | |
uint8_t padding[4]; | |
} NvPartTableHeaderSecure; | |
typedef struct NvPartitionTableEntryRec | |
{ | |
uint32_t PartitionId; // 4 | |
char PartitionName[4]; // 4 | |
NvFsMountInfo MountInfo; // 38 | |
NvPartInfo PartInfo; // 52 | |
} NvPartitionTableEntry; | |
typedef struct NvPartitionTableRec | |
{ | |
NvPartTableHeaderInsecure InsecureHeader; | |
NvPartTableHeaderSecure SecureHeader; | |
NvPartitionTableEntry TableEntry[18]; | |
} NvPartitionTable; | |
int parse_table(char *table) | |
{ | |
int i=0, b=0; | |
NvPartitionTable *tegra = (NvPartitionTable *)table; | |
printf("(Insecure Header)\n"); | |
printf("Insecure Magic: %08llX\n", tegra->InsecureHeader.Magic); | |
printf("Insecure Version: %04X\n", tegra->InsecureHeader.InsecureVersion); | |
printf("Insecure Length: 0x%X\n", tegra->InsecureHeader.InsecureLength); | |
printf("Hash: "); | |
for (i=0; i<16; i++) | |
{ | |
printf("%02x", tegra->InsecureHeader.Signature[i]); | |
}; | |
printf("\n\n"); | |
printf("(Secure Header)\n"); | |
printf("Random Data: "); | |
for (i=0; i<16; i++) | |
{ | |
printf("%02X", tegra->SecureHeader.RandomData[i]); | |
} | |
printf("\n"); | |
printf("Secure Magic: %08llX\n", tegra->SecureHeader.SecureMagic); | |
printf("Secure Version: %04X\n", tegra->SecureHeader.SecureVersion); | |
printf("Secure Length: 0x%X\n", tegra->SecureHeader.SecureLength); | |
printf("Partitions: %d\n", tegra->SecureHeader.NumPartitions); | |
printf("\n\n"); | |
printf("[Partition Table Entries]\n\n"); | |
for (i=0; i<18; i++) | |
{ | |
if (tegra->TableEntry[i].PartitionId >= 128) break; | |
printf("(%s)\n\n", tegra->TableEntry[i].PartitionName); | |
printf("Partition ID: [0x%X]\n", tegra->TableEntry[i].PartitionId); | |
printf("Device ID: [%X]\n", tegra->TableEntry[i].MountInfo.DeviceId); | |
printf("Device Instance: [%X]\n", tegra->TableEntry[i].MountInfo.DeviceInstance); | |
printf("Device Attributes: [%X]\n", tegra->TableEntry[i].MountInfo.DeviceAttr); | |
printf("Mount Path: [%s]\n", tegra->TableEntry[i].MountInfo.MountPath); | |
printf("Filesystem Type: [%X]\n", tegra->TableEntry[i].MountInfo.FileSystemType); | |
printf("Filesystem Attributes: [%X]\n", tegra->TableEntry[i].MountInfo.FileSystemAttr); | |
printf("Partition Attributes: [%X]\n", tegra->TableEntry[i].PartInfo.PartitionAttr); | |
printf("Logical Sector Address: [0x%016llX]\n", tegra->TableEntry[i].PartInfo.LogicalSectorAddress); | |
printf("Number of Logical Sectors: [0x%016llX]\n", tegra->TableEntry[i].PartInfo.NumLogicalSectors); | |
printf("Start Physical Sector Address: [0x%016llX]\n", tegra->TableEntry[i].PartInfo.StartPhysicalSectorAddress); | |
printf("End Physical Sector Address: [0x%016llX]\n", tegra->TableEntry[i].PartInfo.EndPhysicalSectorAddress); | |
printf("Partition Type: [0x%X]\n", tegra->TableEntry[i].PartInfo.PartitionType); | |
printf("\n\n"); | |
} | |
return 0; | |
} | |
int parse_header(char* image) | |
{ | |
FILE* inf; | |
int i = 0; | |
uint32_t size, result; | |
char* data; | |
inf = fopen(image, "rb"); | |
if (!inf) | |
{ | |
printf("Error opening image %s\n", image); | |
return 1; | |
} | |
fseek(inf, 0, SEEK_END); | |
size = ftell(inf); | |
rewind(inf); | |
data = (char*)malloc(sizeof(char)*(size)); | |
if (!data) | |
{ | |
printf("Failed to allocate buffer!\n"); | |
return 1; | |
} | |
result = fread((data), 1, size, inf); | |
if (result != size) | |
{ | |
printf("Error reading image %s\n\r", image); | |
return 1; | |
} | |
fclose(inf); | |
result = *(uint32_t*)data; | |
if (result == 0x8F9E8D8B) | |
{ | |
printf("Detected Nvidia Tegra partition table!\n\n"); | |
parse_table(data); | |
} | |
else | |
{ | |
printf("Image could not be identified!\n\n"); | |
} | |
free(data); | |
return 0; | |
} | |
int main(int argc, char* argv[]) | |
{ | |
char image[200] = {0}; | |
if (argc < 2 || argc > 2) | |
{ | |
printf("No partition file specified!\n"); | |
} | |
else | |
{ | |
sscanf(argv[1], "%s", image); | |
printf("Processing...\n\n"); | |
parse_header(image); | |
} | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment