-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathpacker.cpp
More file actions
109 lines (88 loc) · 2.78 KB
/
packer.cpp
File metadata and controls
109 lines (88 loc) · 2.78 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
#include <fstream>
#include <iostream>
#include <string>
#include <cstdio>
#include <stdint.h>
#include <cstring>
#include <vector>
#include <iterator>
using std::vector;
vector<char> readToBuffer(FILE *fileDescriptor) {
const unsigned N = 1024;
fseek(fileDescriptor, 0, SEEK_END);
auto endPos = ftell(fileDescriptor);
rewind(fileDescriptor);
vector<char> total(endPos);
auto writeHead = std::begin(total);
for (int c = 0; c < endPos; ++c) {
char buffer[N];
size_t read = fread((void *) &buffer[0], 1, N, fileDescriptor);
if (read) {
for (unsigned int c = 0; c < read; ++c) {
*writeHead = (buffer[c]);
writeHead = std::next(writeHead);
}
}
if (read < N) {
break;
}
}
return total;
}
struct Entry {
public:
Entry(std::string path, std::string key);
vector<char> mContent;
std::string id;
uint32_t offset = 0;
};
Entry::Entry(std::string path, std::string key) : id(key) {
FILE *in = fopen(path.c_str(), "rb");
mContent = readToBuffer(in);
fclose(in);
}
void writeHeader(FILE *file, uint16_t entries) {
fwrite(&entries, 2, 1, file);
}
int main(int argc, char **argv) {
int c = argc;
vector<Entry> files;
while (--c) {
std::string filename = argv[c];
std::cout << "adding " << filename << std::endl;
files.emplace_back(filename, filename.substr(filename.find('/') + 1));
}
FILE *file = fopen("data.pfs", "wb");
uint32_t accOffset = 0;
uint16_t entries = files.size();
writeHeader(file, entries);
accOffset += 2;
for (uint16_t e = 0; e < entries; ++e) {
accOffset += 4 + 1 + files[e].id.length() + 1;
}
std::cout << "base offset " << accOffset << std::endl;
for (uint16_t e = 0; e < entries; ++e) {
files[e].offset = accOffset;
std::cout << "Offset for " << files[e].id << " = " << accOffset << std::endl;
accOffset += 4 + files[e].mContent.size();
}
for (uint16_t e = 0; e < entries; ++e) {
std::cout << "entry " << files[e].id << " starting at " << ftell(file) << std::endl;
uint32_t offset = files[e].offset;
const char *name = files[e].id.c_str();
uint8_t strLen = std::strlen(name);
fwrite(&offset, 4, 1, file);
fwrite(&strLen, 1, 1, file);
fwrite(name, strLen + 1, 1, file);
}
for (uint16_t e = 0; e < entries; ++e) {
uint32_t size = files[e].mContent.size();
std::cout << "writing a file " << files[e].id << " with " << size << " bytes at " << ftell(file) << std::endl;
fwrite(&size, 4, 1, file);
for (const auto &c : files[e].mContent) {
fwrite(&c, 1, 1, file);
}
}
fclose(file);
return 0;
}