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
|
#ifdef RYML_SINGLE_HEADER
#include <ryml_all.hpp>
#else
#include <c4/yml/std/std.hpp>
#include <c4/yml/parse.hpp>
#endif
#include <test_suite/test_suite_events.hpp>
#include <c4/fs/fs.hpp>
#include <cstdio>
#include <stdexcept>
using namespace c4;
using namespace c4::yml;
void usage(const char *exename);
std::string load_file(csubstr filename);
void report_error(const char* msg, size_t length, Location loc, FILE *f);
int main(int argc, const char *argv[])
{
if(argc < 2)
{
usage(argv[0]);
return 1;
}
Callbacks callbacks = {};
callbacks.m_error = [](const char *msg, size_t msg_len, Location location, void *)
{
report_error(msg, msg_len, location, stderr);
throw std::runtime_error({msg, msg_len});
};
try {
Tree tree(callbacks);
csubstr filename = to_csubstr(argv[1]);
std::string evt, src = load_file(filename);
tree.reserve(to_substr(src).count('\n'));
parse_in_place(filename, to_substr(src), &tree);
emit_events(&evt, tree);
std::fwrite(evt.data(), 1, evt.size(), stdout);
}
catch(std::exception const&)
{
return 1;
}
return 0;
}
//-----------------------------------------------------------------------------
void usage(const char *exename)
{
std::printf(R"(usage:
%s - # read from stdin
%s <file> # read from file
)", exename, exename);
}
std::string load_file(csubstr filename)
{
if(filename == "-") // read from stdin
{
std::string buf;
for(int c = std::getchar(); c != EOF; c = std::getchar())
{
buf.push_back((char)c);
if(buf.size() == buf.capacity())
buf.reserve(2u * (buf.capacity() >= 128u ? buf.capacity() : 128u));
}
return buf;
}
C4_CHECK_MSG(fs::path_exists(filename.str), "cannot find file: %s (cwd=%s)", filename.str, fs::cwd<std::string>().c_str());
return fs::file_get_contents<std::string>(filename.str);
}
void report_error(const char* msg, size_t length, Location loc, FILE *f)
{
if(!loc.name.empty())
{
fwrite(loc.name.str, 1, loc.name.len, f);
fputc(':', f);
}
fprintf(f, "%zu:", loc.line);
if(loc.col)
fprintf(f, "%zu:", loc.col);
if(loc.offset)
fprintf(f, " (%zuB):", loc.offset);
fputc(' ', f);
fprintf(f, "%.*s\n", (int)length, msg);
fflush(f);
}
|