mirror of
https://github.com/SabreTools/SabreTools.Serialization.git
synced 2026-02-04 05:36:12 +00:00
Compare commits
747 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
d15b4d7d23 | ||
|
|
60e6a75d5e | ||
|
|
484415d0e5 | ||
|
|
0ef9b447c4 | ||
|
|
8f64e2defd | ||
|
|
fbdadce129 | ||
|
|
d3e7abfaa3 | ||
|
|
b2279e97b2 | ||
|
|
7cf969336f | ||
|
|
f73d48166a | ||
|
|
53af618fe4 | ||
|
|
5d2cf58477 | ||
|
|
664e7dce28 | ||
|
|
14a8f00864 | ||
|
|
0b889fdc06 | ||
|
|
e336efc149 | ||
|
|
4cd52162eb | ||
|
|
eab9fff711 | ||
|
|
d4f3511060 | ||
|
|
ed12bbb35c | ||
|
|
aa4629fe99 | ||
|
|
1950f23cf4 | ||
|
|
ca7c88cef6 | ||
|
|
10848e6c51 | ||
|
|
f5d0f065c1 | ||
|
|
17b0573b0b | ||
|
|
7f1d843d96 | ||
|
|
cc4837c1d1 | ||
|
|
588ee5bfe4 | ||
|
|
e9b1b2750f | ||
|
|
1d6fa06e97 | ||
|
|
2c22924239 | ||
|
|
eb01dd1e25 | ||
|
|
0a3cb79b1c | ||
|
|
da9eace8cc | ||
|
|
526a02b8b6 | ||
|
|
658c7a1c3b | ||
|
|
af84474795 | ||
|
|
42913c6732 | ||
|
|
2cdf544518 | ||
|
|
652ec58238 | ||
|
|
f8531daa5c | ||
|
|
e9e89b0b43 | ||
|
|
55e788a894 | ||
|
|
b28bb93ccb | ||
|
|
367aab0f83 | ||
|
|
9dcf3b9e0a | ||
|
|
3c514110ce | ||
|
|
c9b0c2dace | ||
|
|
d575b6977e | ||
|
|
a00e6a5e2d | ||
|
|
1b9ae83e8c | ||
|
|
8b91eb1caf | ||
|
|
2a6a7b5e9a | ||
|
|
a85943866e | ||
|
|
797fb519c1 | ||
|
|
3ba9d56363 | ||
|
|
04cd4e4056 | ||
|
|
348e170654 | ||
|
|
f5a4ca6276 | ||
|
|
672c010aa7 | ||
|
|
2459d88951 | ||
|
|
350d1c8d31 | ||
|
|
98a3842a3e | ||
|
|
b52a4469ee | ||
|
|
e3143e21ba | ||
|
|
1bf2181fd3 | ||
|
|
1460635aab | ||
|
|
935ec00c86 | ||
|
|
473b6de09b | ||
|
|
ba75f2ac2c | ||
|
|
a230b39fbc | ||
|
|
8e963ac62a | ||
|
|
eaaa89847d | ||
|
|
ef76166978 | ||
|
|
72912586a1 | ||
|
|
fb241a4036 | ||
|
|
368c8b0533 | ||
|
|
4010325e65 | ||
|
|
11dd75ad95 | ||
|
|
d0480a1311 | ||
|
|
2be33b845d | ||
|
|
2ad42e3a0f | ||
|
|
5d1f83800b | ||
|
|
30e89a7943 | ||
|
|
61f5dc4cf2 | ||
|
|
d056c179ed | ||
|
|
b9c4bfc67e | ||
|
|
6ab5ee0ae0 | ||
|
|
94c1a86702 | ||
|
|
af6dd6a7fc | ||
|
|
45d4926d4c | ||
|
|
ce016c5eb0 | ||
|
|
2225c1f2d8 | ||
|
|
2d0c0d5845 | ||
|
|
60f1756cbb | ||
|
|
738a1d250a | ||
|
|
c8e65e1e30 | ||
|
|
ecb09ce6f2 | ||
|
|
72a1484a71 | ||
|
|
de31c10c7c | ||
|
|
84483c229c | ||
|
|
b7e35a8fa8 | ||
|
|
8c190a26a5 | ||
|
|
2e5705125b | ||
|
|
daaa92def0 | ||
|
|
86ec97678e | ||
|
|
d74b82dc55 | ||
|
|
821ade2006 | ||
|
|
3ee999dccd | ||
|
|
f91bda51e1 | ||
|
|
47255fc331 | ||
|
|
f7488bed04 | ||
|
|
a94b3a82c4 | ||
|
|
1c8f64f5e6 | ||
|
|
a015e4df3f | ||
|
|
2489a49924 | ||
|
|
d418fbd60d | ||
|
|
cc2e7704e6 | ||
|
|
a980a56dfa | ||
|
|
da588e3bc0 | ||
|
|
8b6f45d9b7 | ||
|
|
9bdfe33baf | ||
|
|
13d338f615 | ||
|
|
36a8641c8d | ||
|
|
7bde6f99fc | ||
|
|
45428ce991 | ||
|
|
8eb5898ef6 | ||
|
|
556e1c972c | ||
|
|
df8f3e7122 | ||
|
|
da1d575806 | ||
|
|
c4d40a1dde | ||
|
|
912de926d0 | ||
|
|
c60fc1e31f | ||
|
|
386e607887 | ||
|
|
94c9b8d057 | ||
|
|
5f81275b10 | ||
|
|
37c484411b | ||
|
|
ad1f890742 | ||
|
|
2924529fa7 | ||
|
|
ebe675cae1 | ||
|
|
a40c666775 | ||
|
|
2ea060d3b3 | ||
|
|
f8a67839dd | ||
|
|
2773b12c9b | ||
|
|
929e12f976 | ||
|
|
8fbc6c4662 | ||
|
|
797378e9c8 | ||
|
|
113464a7d1 | ||
|
|
a13c837202 | ||
|
|
48765f1ae5 | ||
|
|
091ee56368 | ||
|
|
015a971147 | ||
|
|
7575a01a28 | ||
|
|
7aa14cafea | ||
|
|
db10721386 | ||
|
|
6112cf8d60 | ||
|
|
50caeba322 | ||
|
|
b3499984b3 | ||
|
|
a5609a7a82 | ||
|
|
8626a87860 | ||
|
|
fa31cd0e98 | ||
|
|
6b6b7c6289 | ||
|
|
baa3b272ab | ||
|
|
d7c4f244cc | ||
|
|
e21d226564 | ||
|
|
6ff6a7d4a4 | ||
|
|
daf19a561c | ||
|
|
26226a75ff | ||
|
|
4473edf476 | ||
|
|
54cf0a6470 | ||
|
|
0eb8f7e538 | ||
|
|
23b72c65ba | ||
|
|
db7d89600c | ||
|
|
67d51ad1d6 | ||
|
|
56b71cf7fe | ||
|
|
e0ec2a521f | ||
|
|
e8589ac7b5 | ||
|
|
21e425acee | ||
|
|
ee316052ae | ||
|
|
3463936ae0 | ||
|
|
5ff947b279 | ||
|
|
fdf2ea84ec | ||
|
|
ad9b001b6a | ||
|
|
1308571c10 | ||
|
|
b8cb3419c1 | ||
|
|
02533cf947 | ||
|
|
bf8bd04dc7 | ||
|
|
1894376ab6 | ||
|
|
c789e4df44 | ||
|
|
884685de4a | ||
|
|
7fda7be457 | ||
|
|
5daf759033 | ||
|
|
589ab0896a | ||
|
|
7645ab978f | ||
|
|
e6497289da | ||
|
|
95a9f4769d | ||
|
|
7917601f7a | ||
|
|
3400238fc5 | ||
|
|
cbd335c6aa | ||
|
|
9feaadd32a | ||
|
|
2ec008b3b7 | ||
|
|
c9a462a1c6 | ||
|
|
ab44aa7e68 | ||
|
|
9b9d3176ec | ||
|
|
5dda3e2c81 | ||
|
|
4b8dc12c98 | ||
|
|
044e4c4c75 | ||
|
|
2149630865 | ||
|
|
3d435a1d7e | ||
|
|
f2d993a958 | ||
|
|
7bf75b8dc5 | ||
|
|
dfbdce1dc8 | ||
|
|
63f5566e65 | ||
|
|
4b0f43f6c0 | ||
|
|
98e1ef7362 | ||
|
|
4e0ffcb3c8 | ||
|
|
a93a46d6c0 | ||
|
|
e163302522 | ||
|
|
838afc35c3 | ||
|
|
3a62bfab57 | ||
|
|
560b3a246c | ||
|
|
4360916750 | ||
|
|
3f31edc1c0 | ||
|
|
bd874d436b | ||
|
|
fbc47425f4 | ||
|
|
c9df6ff059 | ||
|
|
ef6ff85e96 | ||
|
|
bb93792f57 | ||
|
|
1f7ab4fccb | ||
|
|
2535e82618 | ||
|
|
66d80c8523 | ||
|
|
834a17fe82 | ||
|
|
ea85167e06 | ||
|
|
e007a06dda | ||
|
|
02f9e1e935 | ||
|
|
21b7d431a7 | ||
|
|
307b932f87 | ||
|
|
6983d1cd3c | ||
|
|
a193c9bb3c | ||
|
|
aa67c7ad6d | ||
|
|
70fc686249 | ||
|
|
c87a456a46 | ||
|
|
456bb1e95b | ||
|
|
b0b334103d | ||
|
|
78851e3b57 | ||
|
|
850a883e14 | ||
|
|
6e0ced5ffe | ||
|
|
64cd8febaa | ||
|
|
6fbe1cffaa | ||
|
|
601e781ef9 | ||
|
|
d26ad35573 | ||
|
|
b70c510734 | ||
|
|
29a7158488 | ||
|
|
1227ca020a | ||
|
|
cd7e6ff98d | ||
|
|
510a0f77f6 | ||
|
|
6d1dabb1db | ||
|
|
2e337891da | ||
|
|
d49e18a83e | ||
|
|
c14560ec18 | ||
|
|
e3e31cd9f2 | ||
|
|
adf9627045 | ||
|
|
c7b03c7765 | ||
|
|
b5f83215d5 | ||
|
|
96e3fc5533 | ||
|
|
828e7dda03 | ||
|
|
8ef50c30d5 | ||
|
|
cbe1d5b608 | ||
|
|
7123a9e986 | ||
|
|
af5996b972 | ||
|
|
15e947784b | ||
|
|
1b382c201e | ||
|
|
8deca4fb0c | ||
|
|
96c4372609 | ||
|
|
ca7a109037 | ||
|
|
c54f5b3c5d | ||
|
|
652942ab9f | ||
|
|
2cc19a9c36 | ||
|
|
6ffb3f4bbd | ||
|
|
bab4278318 | ||
|
|
013d18a426 | ||
|
|
e94e27910e | ||
|
|
34cea6e74a | ||
|
|
640e160863 | ||
|
|
3100963250 | ||
|
|
2086358762 | ||
|
|
ae273c589d | ||
|
|
a229015fcd | ||
|
|
b001680674 | ||
|
|
e684133f72 | ||
|
|
2b020eecc7 | ||
|
|
78f4d6faca | ||
|
|
f07b7a049e | ||
|
|
544637779c | ||
|
|
38b6427e4e | ||
|
|
e36822a19c | ||
|
|
e1a114976f | ||
|
|
5ba9ab3457 | ||
|
|
36edf9ed54 | ||
|
|
e788ffa851 | ||
|
|
e0d819b88d | ||
|
|
e3b216ad09 | ||
|
|
55d0fd452d | ||
|
|
089fd02b2e | ||
|
|
8cfd820dcd | ||
|
|
67ed9860fe | ||
|
|
ee924e3a34 | ||
|
|
9e5085ba79 | ||
|
|
dbfdbbff20 | ||
|
|
21dc72bf11 | ||
|
|
c8295c4724 | ||
|
|
44b4dd3d1b | ||
|
|
7e543c6acb | ||
|
|
63514d149f | ||
|
|
d7e559749d | ||
|
|
a2be40fcbc | ||
|
|
771df5c372 | ||
|
|
2d3d6348ad | ||
|
|
a2bf15f0bc | ||
|
|
0aa25df88f | ||
|
|
36afb1c0ee | ||
|
|
c9d61906fb | ||
|
|
d8440a01d3 | ||
|
|
74d92312ef | ||
|
|
0dc9823d2b | ||
|
|
9c69737073 | ||
|
|
66187dcf04 | ||
|
|
79943560bc | ||
|
|
b3321f9c9a | ||
|
|
428c269a49 | ||
|
|
e84964a321 | ||
|
|
0394ea5356 | ||
|
|
852b086920 | ||
|
|
b7fceee2b7 | ||
|
|
ecf6c957c9 | ||
|
|
5e0b0070ff | ||
|
|
9934bc31a3 | ||
|
|
7b4711f5cf | ||
|
|
844066815d | ||
|
|
3a6293e696 | ||
|
|
3210b8601d | ||
|
|
181788802d | ||
|
|
4b627ce776 | ||
|
|
8b799bb5c8 | ||
|
|
5bc8336fce | ||
|
|
4f9f8ddcec | ||
|
|
29f1f63ef8 | ||
|
|
48ecdff5f7 | ||
|
|
411acd2d5a | ||
|
|
e6742fe889 | ||
|
|
b6561719a7 | ||
|
|
2bf3d6f9a6 | ||
|
|
b2700b5975 | ||
|
|
95b28874da | ||
|
|
4934ee837c | ||
|
|
3cbfd5cd10 | ||
|
|
da28ce310b | ||
|
|
ac6d93a3b9 | ||
|
|
104028204d | ||
|
|
d3e61b42dd | ||
|
|
6351cabb62 | ||
|
|
ddef42126b | ||
|
|
9dd39a7f02 | ||
|
|
ca7f7e97e7 | ||
|
|
8a40349b0c | ||
|
|
6ec6fa4973 | ||
|
|
f0644710e6 | ||
|
|
34048726ab | ||
|
|
60ce6c9370 | ||
|
|
554fccc236 | ||
|
|
7611c043c3 | ||
|
|
976d793474 | ||
|
|
f0f997fadd | ||
|
|
0ce3c9892d | ||
|
|
9743565285 | ||
|
|
fcfe9e4790 | ||
|
|
be36432296 | ||
|
|
fb725bff19 | ||
|
|
2384cf9f9f | ||
|
|
1261930fd9 | ||
|
|
120de4e49f | ||
|
|
354a51769b | ||
|
|
a9f937baa3 | ||
|
|
1790d82a6e | ||
|
|
261c20e95a | ||
|
|
ed6556b1f0 | ||
|
|
a86af8c32a | ||
|
|
1670ab45a0 | ||
|
|
7dc4750f3b | ||
|
|
b5f366680d | ||
|
|
fa9e9a0b2b | ||
|
|
2239b82a4b | ||
|
|
3b631678f5 | ||
|
|
2b111a9688 | ||
|
|
0bda1f4f88 | ||
|
|
7d50e0e1c5 | ||
|
|
224a4caab0 | ||
|
|
b4689da404 | ||
|
|
af66657399 | ||
|
|
0f3e2d8275 | ||
|
|
d664b6defc | ||
|
|
adbf74a6e0 | ||
|
|
7eb401efed | ||
|
|
ba97381b99 | ||
|
|
3de92de225 | ||
|
|
01a195c8aa | ||
|
|
12d43ef68a | ||
|
|
0df806a6d1 | ||
|
|
f8c713b260 | ||
|
|
4d0122f97c | ||
|
|
7874950a7a | ||
|
|
577afc8947 | ||
|
|
5a3e69e8ed | ||
|
|
67ee595eb4 | ||
|
|
992f8eaeb8 | ||
|
|
dde5a57136 | ||
|
|
ae49950ae6 | ||
|
|
b56ea3a479 | ||
|
|
03d4ea046d | ||
|
|
248741b2c0 | ||
|
|
ef307664e2 | ||
|
|
05c497a5a0 | ||
|
|
f8239780b2 | ||
|
|
ff12bf8205 | ||
|
|
0c3adf055c | ||
|
|
d9b1f5d45f | ||
|
|
5ab3dded30 | ||
|
|
991d9ead27 | ||
|
|
25c0d036f2 | ||
|
|
c06d8151e6 | ||
|
|
0e9ba25637 | ||
|
|
bd7ca7f3a7 | ||
|
|
26146554a3 | ||
|
|
884746a5a1 | ||
|
|
ab0e68110c | ||
|
|
e166d18903 | ||
|
|
2152ba43a8 | ||
|
|
f42c5d04ee | ||
|
|
ea535fa393 | ||
|
|
e6d118e8cc | ||
|
|
35a921e436 | ||
|
|
25cc3e42f3 | ||
|
|
14344756da | ||
|
|
cb270d3185 | ||
|
|
d5cef39f1b | ||
|
|
b782af427e | ||
|
|
6b503a0733 | ||
|
|
4a3741312e | ||
|
|
aed140a684 | ||
|
|
5b93df9703 | ||
|
|
5ae162400c | ||
|
|
f828b57159 | ||
|
|
d0cfc67f07 | ||
|
|
2f48c3110c | ||
|
|
6cdc35c82f | ||
|
|
9214a22cc9 | ||
|
|
5ba1156245 | ||
|
|
cb91cdff1d | ||
|
|
4df6a4e79d | ||
|
|
5b82a48267 | ||
|
|
8f70c50a48 | ||
|
|
5fe4d81fa4 | ||
|
|
7d3addbf0a | ||
|
|
b7d5873eb7 | ||
|
|
4e40cc19d5 | ||
|
|
1bc9316bc1 | ||
|
|
c995ec1dca | ||
|
|
4d2fbbae04 | ||
|
|
2776928946 | ||
|
|
8cc87c6540 | ||
|
|
3c212022aa | ||
|
|
511c4d09e5 | ||
|
|
d7eba27dc5 | ||
|
|
09370618ca | ||
|
|
2197167088 | ||
|
|
b527635fe7 | ||
|
|
695309bc32 | ||
|
|
97b2f68ec7 | ||
|
|
593044dbf3 | ||
|
|
1fcf44fb8d | ||
|
|
a2a472baf9 | ||
|
|
b5b4a50d94 | ||
|
|
f1b5464052 | ||
|
|
2c0224db22 | ||
|
|
1e78eecb40 | ||
|
|
3626faea60 | ||
|
|
a0177f1174 | ||
|
|
db5fe4a2cd | ||
|
|
5716143168 | ||
|
|
2a59b23149 | ||
|
|
bdbec4ed02 | ||
|
|
25193f1805 | ||
|
|
4840c816a2 | ||
|
|
d0a8e3770b | ||
|
|
1cf3d50864 | ||
|
|
d1b98f7d6d | ||
|
|
4bc87ff812 | ||
|
|
e1df11b360 | ||
|
|
34606a4f04 | ||
|
|
c4c5fc4bf6 | ||
|
|
cd87ce5373 | ||
|
|
90fc16b888 | ||
|
|
c2d0b71d22 | ||
|
|
e54473682c | ||
|
|
1c8d64d98c | ||
|
|
a19437f42f | ||
|
|
855e2f2c77 | ||
|
|
bd3cf88123 | ||
|
|
e4578ad3fc | ||
|
|
39e56ef864 | ||
|
|
51b77da760 | ||
|
|
4b83219a9b | ||
|
|
3ed07dd299 | ||
|
|
bb7daed7f6 | ||
|
|
0c84c47752 | ||
|
|
c18a185474 | ||
|
|
8ff66b04d8 | ||
|
|
94d6556e04 | ||
|
|
6d960265e4 | ||
|
|
cf4ca76e10 | ||
|
|
c7760e9903 | ||
|
|
d51bedceb6 | ||
|
|
125dc021d5 | ||
|
|
5bce481648 | ||
|
|
20153f62cf | ||
|
|
e302dfccf1 | ||
|
|
594b841490 | ||
|
|
40c354f79f | ||
|
|
b77959f300 | ||
|
|
59d6026a2b | ||
|
|
14226d1270 | ||
|
|
955f4da708 | ||
|
|
700b0359ea | ||
|
|
fe95b894d7 | ||
|
|
38a2712a8f | ||
|
|
d1ea091574 | ||
|
|
6bc812fc2f | ||
|
|
61b89fbd72 | ||
|
|
a2c065bdf2 | ||
|
|
88479f674b | ||
|
|
5edbacde74 | ||
|
|
67fc51224b | ||
|
|
101f3294b4 | ||
|
|
6c5622f732 | ||
|
|
f2a6fe1445 | ||
|
|
b0b593443f | ||
|
|
9b05185add | ||
|
|
17316da536 | ||
|
|
f3ca4dd989 | ||
|
|
e2b7bdac8c | ||
|
|
f86f6dc438 | ||
|
|
2bac0ed505 | ||
|
|
ae4078bb7f | ||
|
|
afaffbd9a2 | ||
|
|
b878e59e2e | ||
|
|
4bb3f625dd | ||
|
|
b7978cafa5 | ||
|
|
17f376c76f | ||
|
|
2774fdf158 | ||
|
|
11081efcb0 | ||
|
|
1b412c3027 | ||
|
|
73ec66e627 | ||
|
|
4ae4cd80b1 | ||
|
|
6eb27c66fc | ||
|
|
f96fd17fd3 | ||
|
|
c255a2494d | ||
|
|
86a9846300 | ||
|
|
db877d253c | ||
|
|
0acf1e3b08 | ||
|
|
362ed3a9b6 | ||
|
|
758878a229 | ||
|
|
ffb6dfc333 | ||
|
|
66da74e00a | ||
|
|
d41a0045cb | ||
|
|
b65629ba0e | ||
|
|
9518e6d1a0 | ||
|
|
4f374ee885 | ||
|
|
afa239056e | ||
|
|
886825af11 | ||
|
|
198de925aa | ||
|
|
3f7b71e9a5 | ||
|
|
95baaf8603 | ||
|
|
3673264bab | ||
|
|
64fb5a6b63 | ||
|
|
e9c959ccdb | ||
|
|
4b7487e92e | ||
|
|
52dbcffd8e | ||
|
|
24ae354bc2 | ||
|
|
b30b91fd91 | ||
|
|
efb63afc74 | ||
|
|
16706f7169 | ||
|
|
d7c32676b5 | ||
|
|
c8c45446bc | ||
|
|
f4de2e27d7 | ||
|
|
970fcbd93b | ||
|
|
57d1cd7f1e | ||
|
|
522fc372fa | ||
|
|
7141690fcb | ||
|
|
c7d9177e68 | ||
|
|
00b3ea40d9 | ||
|
|
c9afe939dc | ||
|
|
4171ae6516 | ||
|
|
35a42c49d5 | ||
|
|
e4dbf56b49 | ||
|
|
76eeb10c47 | ||
|
|
9fa73ad54f | ||
|
|
6034a4fd06 | ||
|
|
9d15310b04 | ||
|
|
f04ec3e465 | ||
|
|
0071e7a462 | ||
|
|
d697461cc2 | ||
|
|
517ff00a0f | ||
|
|
d06017c045 | ||
|
|
1b819d96a5 | ||
|
|
ad2bfc31bc | ||
|
|
66b4f12fb3 | ||
|
|
40de2575bb | ||
|
|
be4a95fe91 | ||
|
|
c685b5e679 | ||
|
|
99baeba735 | ||
|
|
bc6b6d39da | ||
|
|
2bb814e170 | ||
|
|
3bf78c78e3 | ||
|
|
e38ecaec4c | ||
|
|
af40c78b56 | ||
|
|
12b206f9fa | ||
|
|
2cc51ba089 | ||
|
|
52f0846d5d | ||
|
|
3fa8848e77 | ||
|
|
41276e3d7e | ||
|
|
4cef93c95e | ||
|
|
cdd999ee03 | ||
|
|
4f253323db | ||
|
|
351f749e20 | ||
|
|
1e83fc4b9a | ||
|
|
c532bd1063 | ||
|
|
e4631a8176 | ||
|
|
ee8dad0c87 | ||
|
|
4163b2f22a | ||
|
|
6aaf3afa38 | ||
|
|
2a7eb44281 | ||
|
|
08bbc93793 | ||
|
|
789478df13 | ||
|
|
cd4f1c9d97 | ||
|
|
1a2e9fb942 | ||
|
|
d0865739de | ||
|
|
0696bbab72 | ||
|
|
4b4c17ac24 | ||
|
|
d768172da1 | ||
|
|
2a4d24309d | ||
|
|
bc01ce4552 | ||
|
|
ef0efe66bd | ||
|
|
7c21f65723 | ||
|
|
cec53e907f | ||
|
|
006ced0430 | ||
|
|
bee6c0ba11 | ||
|
|
3cb880ff3f | ||
|
|
f1d54e4a14 | ||
|
|
f4aaed7f9c | ||
|
|
46ad76c5d2 | ||
|
|
8f731cebc8 | ||
|
|
6dbf9dacd6 | ||
|
|
94ab760c67 | ||
|
|
4ed3880bad | ||
|
|
ff8dcd30a5 | ||
|
|
8ced91d0fa | ||
|
|
f2c6fa2b8e | ||
|
|
9b1bacd167 | ||
|
|
964c97200c | ||
|
|
a3f3384ac9 | ||
|
|
8b546fbf27 | ||
|
|
15da711087 | ||
|
|
bfee7dd449 | ||
|
|
9de2a91e80 | ||
|
|
bf50c801b2 | ||
|
|
c19a4a94f4 | ||
|
|
b6fe94116b | ||
|
|
bcf604c773 | ||
|
|
74984a9114 | ||
|
|
8c1e241286 | ||
|
|
f666d737cb | ||
|
|
a01609f1d1 | ||
|
|
8ca9ccaf00 | ||
|
|
fc5374108c | ||
|
|
15452ded52 | ||
|
|
49c6c4412b | ||
|
|
cfc53f66a8 | ||
|
|
ec1fb7247c | ||
|
|
54b1eef8ae | ||
|
|
f448314309 | ||
|
|
c4e8debb15 | ||
|
|
822839c813 | ||
|
|
27d36a11ca | ||
|
|
92d9ca932d | ||
|
|
69e1f5ff0b | ||
|
|
d265c14841 | ||
|
|
1148245226 | ||
|
|
f53d9f94e6 | ||
|
|
4e3d832834 | ||
|
|
0713dfafb2 | ||
|
|
c0d4f403c3 | ||
|
|
5ed79166cf | ||
|
|
17030cfb9f | ||
|
|
530fa69d3c | ||
|
|
7a5956f599 | ||
|
|
5562768509 | ||
|
|
aa538df229 | ||
|
|
b7b22cba32 | ||
|
|
fc489125d9 | ||
|
|
036589473d | ||
|
|
432ce85f89 | ||
|
|
438e8067eb | ||
|
|
9715507aaf | ||
|
|
b745d4b9f6 | ||
|
|
4271bd86b3 | ||
|
|
88de4be27b | ||
|
|
33905165f7 | ||
|
|
83ec3b6950 | ||
|
|
9b5d51884c | ||
|
|
aaa6422921 | ||
|
|
f24b88031b | ||
|
|
edf9fed751 | ||
|
|
beca747943 | ||
|
|
58e538eff6 | ||
|
|
4f04c8aa89 | ||
|
|
d7c1e4e83a | ||
|
|
975eefdc61 | ||
|
|
d8cd5854ce | ||
|
|
0790fc93b6 | ||
|
|
7f6c128521 | ||
|
|
87df6b3ebd | ||
|
|
2ca7326074 | ||
|
|
3b90af7b3a | ||
|
|
6eda2f2541 | ||
|
|
defe1c53aa | ||
|
|
e5fe0a71ef | ||
|
|
83450f693f | ||
|
|
1f70e1f544 | ||
|
|
4bfc83d5d4 | ||
|
|
7364661900 | ||
|
|
1cafc4079d | ||
|
|
0d62cbd1e9 | ||
|
|
bf753262a5 | ||
|
|
5510b5d19d | ||
|
|
d0f0ade757 | ||
|
|
26b03d8256 |
40
.github/workflows/build_and_test.yml
vendored
Normal file
40
.github/workflows/build_and_test.yml
vendored
Normal file
@@ -0,0 +1,40 @@
|
||||
name: Build and Test
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ "main" ]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
with:
|
||||
submodules: recursive
|
||||
|
||||
- name: Setup .NET
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: |
|
||||
6.0.x
|
||||
8.0.x
|
||||
9.0.x
|
||||
|
||||
- name: Run tests
|
||||
run: dotnet test
|
||||
|
||||
- name: Run publish script
|
||||
run: ./publish-nix.sh -d
|
||||
|
||||
- name: Upload to rolling
|
||||
uses: ncipollo/release-action@v1.14.0
|
||||
with:
|
||||
allowUpdates: True
|
||||
artifacts: "*.nupkg,*.snupkg,*.zip"
|
||||
body: 'Last built commit: ${{ github.sha }}'
|
||||
name: 'Rolling Release'
|
||||
prerelease: True
|
||||
replacesArtifacts: True
|
||||
tag: "rolling"
|
||||
updateOnlyUnreleased: True
|
||||
23
.github/workflows/check_pr.yml
vendored
Normal file
23
.github/workflows/check_pr.yml
vendored
Normal file
@@ -0,0 +1,23 @@
|
||||
name: Build PR
|
||||
|
||||
on: [pull_request]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Setup .NET
|
||||
uses: actions/setup-dotnet@v4
|
||||
with:
|
||||
dotnet-version: |
|
||||
6.0.x
|
||||
8.0.x
|
||||
9.0.x
|
||||
|
||||
- name: Build
|
||||
run: dotnet build
|
||||
|
||||
- name: Run tests
|
||||
run: dotnet test
|
||||
328
.gitignore
vendored
328
.gitignore
vendored
@@ -1,15 +1,7 @@
|
||||
*.swp
|
||||
*.*~
|
||||
project.lock.json
|
||||
.DS_Store
|
||||
*.pyc
|
||||
nupkg/
|
||||
|
||||
# Visual Studio Code
|
||||
.vscode
|
||||
|
||||
# Rider
|
||||
.idea
|
||||
## Ignore Visual Studio temporary files, build results, and
|
||||
## files generated by popular Visual Studio add-ons.
|
||||
##
|
||||
## Get latest from https://github.com/github/gitignore/blob/master/VisualStudio.gitignore
|
||||
|
||||
# User-specific files
|
||||
*.suo
|
||||
@@ -17,6 +9,9 @@ nupkg/
|
||||
*.userosscache
|
||||
*.sln.docstates
|
||||
|
||||
# User-specific files (MonoDevelop/Xamarin Studio)
|
||||
*.userprefs
|
||||
|
||||
# Build results
|
||||
[Dd]ebug/
|
||||
[Dd]ebugPublic/
|
||||
@@ -24,15 +19,312 @@ nupkg/
|
||||
[Rr]eleases/
|
||||
x64/
|
||||
x86/
|
||||
build/
|
||||
bld/
|
||||
[Bb]in/
|
||||
[Oo]bj/
|
||||
[Oo]ut/
|
||||
msbuild.log
|
||||
msbuild.err
|
||||
msbuild.wrn
|
||||
[Ll]og/
|
||||
|
||||
# Visual Studio 2015
|
||||
# Visual Studio 2015/2017 cache/options directory
|
||||
.vs/
|
||||
# Uncomment if you have tasks that create the project's static files in wwwroot
|
||||
#wwwroot/
|
||||
|
||||
# Visual Studio 2017 auto generated files
|
||||
Generated\ Files/
|
||||
|
||||
# MSTest test Results
|
||||
[Tt]est[Rr]esult*/
|
||||
[Bb]uild[Ll]og.*
|
||||
|
||||
# NUNIT
|
||||
*.VisualState.xml
|
||||
TestResult.xml
|
||||
|
||||
# Build Results of an ATL Project
|
||||
[Dd]ebugPS/
|
||||
[Rr]eleasePS/
|
||||
dlldata.c
|
||||
|
||||
# Benchmark Results
|
||||
BenchmarkDotNet.Artifacts/
|
||||
|
||||
# .NET Core
|
||||
project.lock.json
|
||||
project.fragment.lock.json
|
||||
artifacts/
|
||||
**/Properties/launchSettings.json
|
||||
|
||||
# StyleCop
|
||||
StyleCopReport.xml
|
||||
|
||||
# Files built by Visual Studio
|
||||
*_i.c
|
||||
*_p.c
|
||||
*_i.h
|
||||
*.ilk
|
||||
*.meta
|
||||
*.obj
|
||||
*.iobj
|
||||
*.pch
|
||||
*.pdb
|
||||
*.ipdb
|
||||
*.pgc
|
||||
*.pgd
|
||||
*.rsp
|
||||
*.sbr
|
||||
*.tlb
|
||||
*.tli
|
||||
*.tlh
|
||||
*.tmp
|
||||
*.tmp_proj
|
||||
*.log
|
||||
*.vspscc
|
||||
*.vssscc
|
||||
.builds
|
||||
*.pidb
|
||||
*.svclog
|
||||
*.scc
|
||||
|
||||
# Chutzpah Test files
|
||||
_Chutzpah*
|
||||
|
||||
# Visual C++ cache files
|
||||
ipch/
|
||||
*.aps
|
||||
*.ncb
|
||||
*.opendb
|
||||
*.opensdf
|
||||
*.sdf
|
||||
*.cachefile
|
||||
*.VC.db
|
||||
*.VC.VC.opendb
|
||||
|
||||
# Visual Studio profiler
|
||||
*.psess
|
||||
*.vsp
|
||||
*.vspx
|
||||
*.sap
|
||||
|
||||
# Visual Studio Trace Files
|
||||
*.e2e
|
||||
|
||||
# TFS 2012 Local Workspace
|
||||
$tf/
|
||||
|
||||
# Guidance Automation Toolkit
|
||||
*.gpState
|
||||
|
||||
# ReSharper is a .NET coding add-in
|
||||
_ReSharper*/
|
||||
*.[Rr]e[Ss]harper
|
||||
*.DotSettings.user
|
||||
|
||||
# JustCode is a .NET coding add-in
|
||||
.JustCode
|
||||
|
||||
# TeamCity is a build add-in
|
||||
_TeamCity*
|
||||
|
||||
# DotCover is a Code Coverage Tool
|
||||
*.dotCover
|
||||
|
||||
# AxoCover is a Code Coverage Tool
|
||||
.axoCover/*
|
||||
!.axoCover/settings.json
|
||||
|
||||
# Visual Studio code coverage results
|
||||
*.coverage
|
||||
*.coveragexml
|
||||
|
||||
# NCrunch
|
||||
_NCrunch_*
|
||||
.*crunch*.local.xml
|
||||
nCrunchTemp_*
|
||||
|
||||
# MightyMoose
|
||||
*.mm.*
|
||||
AutoTest.Net/
|
||||
|
||||
# Web workbench (sass)
|
||||
.sass-cache/
|
||||
|
||||
# Installshield output folder
|
||||
[Ee]xpress/
|
||||
|
||||
# DocProject is a documentation generator add-in
|
||||
DocProject/buildhelp/
|
||||
DocProject/Help/*.HxT
|
||||
DocProject/Help/*.HxC
|
||||
DocProject/Help/*.hhc
|
||||
DocProject/Help/*.hhk
|
||||
DocProject/Help/*.hhp
|
||||
DocProject/Help/Html2
|
||||
DocProject/Help/html
|
||||
|
||||
# Click-Once directory
|
||||
publish/
|
||||
|
||||
# Publish Web Output
|
||||
*.[Pp]ublish.xml
|
||||
*.azurePubxml
|
||||
# Note: Comment the next line if you want to checkin your web deploy settings,
|
||||
# but database connection strings (with potential passwords) will be unencrypted
|
||||
*.pubxml
|
||||
*.publishproj
|
||||
|
||||
# Microsoft Azure Web App publish settings. Comment the next line if you want to
|
||||
# checkin your Azure Web App publish settings, but sensitive information contained
|
||||
# in these scripts will be unencrypted
|
||||
PublishScripts/
|
||||
|
||||
# NuGet Packages
|
||||
*.nupkg
|
||||
# The packages folder can be ignored because of Package Restore
|
||||
**/[Pp]ackages/*
|
||||
# except build/, which is used as an MSBuild target.
|
||||
!**/[Pp]ackages/build/
|
||||
# Uncomment if necessary however generally it will be regenerated when needed
|
||||
#!**/[Pp]ackages/repositories.config
|
||||
# NuGet v3's project.json files produces more ignorable files
|
||||
*.nuget.props
|
||||
*.nuget.targets
|
||||
|
||||
# Microsoft Azure Build Output
|
||||
csx/
|
||||
*.build.csdef
|
||||
|
||||
# Microsoft Azure Emulator
|
||||
ecf/
|
||||
rcf/
|
||||
|
||||
# Windows Store app package directories and files
|
||||
AppPackages/
|
||||
BundleArtifacts/
|
||||
Package.StoreAssociation.xml
|
||||
_pkginfo.txt
|
||||
*.appx
|
||||
|
||||
# Visual Studio cache files
|
||||
# files ending in .cache can be ignored
|
||||
*.[Cc]ache
|
||||
# but keep track of directories ending in .cache
|
||||
!*.[Cc]ache/
|
||||
|
||||
# Others
|
||||
ClientBin/
|
||||
~$*
|
||||
*~
|
||||
*.dbmdl
|
||||
*.dbproj.schemaview
|
||||
*.jfm
|
||||
*.pfx
|
||||
*.publishsettings
|
||||
orleans.codegen.cs
|
||||
|
||||
# Including strong name files can present a security risk
|
||||
# (https://github.com/github/gitignore/pull/2483#issue-259490424)
|
||||
#*.snk
|
||||
|
||||
# Since there are multiple workflows, uncomment next line to ignore bower_components
|
||||
# (https://github.com/github/gitignore/pull/1529#issuecomment-104372622)
|
||||
#bower_components/
|
||||
|
||||
# RIA/Silverlight projects
|
||||
Generated_Code/
|
||||
|
||||
# Backup & report files from converting an old project file
|
||||
# to a newer Visual Studio version. Backup files are not needed,
|
||||
# because we have git ;-)
|
||||
_UpgradeReport_Files/
|
||||
Backup*/
|
||||
UpgradeLog*.XML
|
||||
UpgradeLog*.htm
|
||||
ServiceFabricBackup/
|
||||
*.rptproj.bak
|
||||
|
||||
# SQL Server files
|
||||
*.mdf
|
||||
*.ldf
|
||||
*.ndf
|
||||
|
||||
# Business Intelligence projects
|
||||
*.rdl.data
|
||||
*.bim.layout
|
||||
*.bim_*.settings
|
||||
*.rptproj.rsuser
|
||||
|
||||
# Microsoft Fakes
|
||||
FakesAssemblies/
|
||||
|
||||
# GhostDoc plugin setting file
|
||||
*.GhostDoc.xml
|
||||
|
||||
# Node.js Tools for Visual Studio
|
||||
.ntvs_analysis.dat
|
||||
node_modules/
|
||||
|
||||
# Visual Studio 6 build log
|
||||
*.plg
|
||||
|
||||
# Visual Studio 6 workspace options file
|
||||
*.opt
|
||||
|
||||
# Visual Studio 6 auto-generated workspace file (contains which files were open etc.)
|
||||
*.vbw
|
||||
|
||||
# Visual Studio LightSwitch build output
|
||||
**/*.HTMLClient/GeneratedArtifacts
|
||||
**/*.DesktopClient/GeneratedArtifacts
|
||||
**/*.DesktopClient/ModelManifest.xml
|
||||
**/*.Server/GeneratedArtifacts
|
||||
**/*.Server/ModelManifest.xml
|
||||
_Pvt_Extensions
|
||||
|
||||
# Paket dependency manager
|
||||
.paket/paket.exe
|
||||
paket-files/
|
||||
|
||||
# FAKE - F# Make
|
||||
.fake/
|
||||
|
||||
# JetBrains Rider
|
||||
.idea/
|
||||
*.sln.iml
|
||||
|
||||
# CodeRush
|
||||
.cr/
|
||||
|
||||
# Python Tools for Visual Studio (PTVS)
|
||||
__pycache__/
|
||||
*.pyc
|
||||
|
||||
# Cake - Uncomment if you are using it
|
||||
# tools/**
|
||||
# !tools/packages.config
|
||||
|
||||
# Tabs Studio
|
||||
*.tss
|
||||
|
||||
# Telerik's JustMock configuration file
|
||||
*.jmconfig
|
||||
|
||||
# BizTalk build output
|
||||
*.btp.cs
|
||||
*.btm.cs
|
||||
*.odx.cs
|
||||
*.xsd.cs
|
||||
|
||||
# OpenCover UI analysis results
|
||||
OpenCover/
|
||||
|
||||
# Azure Stream Analytics local run output
|
||||
ASALocalRun/
|
||||
|
||||
# MSBuild Binary and Structured Log
|
||||
*.binlog
|
||||
|
||||
# NVidia Nsight GPU debugger configuration file
|
||||
*.nvuser
|
||||
|
||||
# MFractors (Xamarin productivity tool) working folder
|
||||
.mfractor/
|
||||
|
||||
3
.gitmodules
vendored
Normal file
3
.gitmodules
vendored
Normal file
@@ -0,0 +1,3 @@
|
||||
[submodule "SabreTools.Serialization/_EXTERNAL/stormlibsharp"]
|
||||
path = SabreTools.Serialization/_EXTERNAL/stormlibsharp
|
||||
url = https://github.com/robpaveza/stormlibsharp.git
|
||||
42
.vscode/launch.json
vendored
Normal file
42
.vscode/launch.json
vendored
Normal file
@@ -0,0 +1,42 @@
|
||||
{
|
||||
// Use IntelliSense to find out which attributes exist for C# debugging
|
||||
// Use hover for the description of the existing attributes
|
||||
// For further information visit https://github.com/OmniSharp/omnisharp-vscode/blob/master/debugger-launchjson.md
|
||||
"version": "0.2.0",
|
||||
"configurations": [
|
||||
{
|
||||
"name": ".NET Core Launch (ExtractionTool)",
|
||||
"type": "coreclr",
|
||||
"request": "launch",
|
||||
"preLaunchTask": "build",
|
||||
// If you have changed target frameworks, make sure to update the program path.
|
||||
"program": "${workspaceFolder}/ExtractionTool/bin/Debug/net9.0/ExtractionTool.dll",
|
||||
"args": [],
|
||||
"cwd": "${workspaceFolder}",
|
||||
// For more information about the 'console' field, see https://aka.ms/VSCode-CS-LaunchJson-Console
|
||||
"console": "internalConsole",
|
||||
"stopAtEntry": false,
|
||||
"justMyCode": false
|
||||
},
|
||||
{
|
||||
"name": ".NET Core Launch (InfoPrint)",
|
||||
"type": "coreclr",
|
||||
"request": "launch",
|
||||
"preLaunchTask": "build",
|
||||
// If you have changed target frameworks, make sure to update the program path.
|
||||
"program": "${workspaceFolder}/InfoPrint/bin/Debug/net9.0/InfoPrint.dll",
|
||||
"args": [],
|
||||
"cwd": "${workspaceFolder}",
|
||||
// For more information about the 'console' field, see https://aka.ms/VSCode-CS-LaunchJson-Console
|
||||
"console": "internalConsole",
|
||||
"stopAtEntry": false,
|
||||
"justMyCode": false
|
||||
},
|
||||
{
|
||||
"name": ".NET Core Attach",
|
||||
"type": "coreclr",
|
||||
"request": "attach",
|
||||
"processId": "${command:pickProcess}"
|
||||
}
|
||||
]
|
||||
}
|
||||
24
.vscode/tasks.json
vendored
Normal file
24
.vscode/tasks.json
vendored
Normal file
@@ -0,0 +1,24 @@
|
||||
{
|
||||
// See https://go.microsoft.com/fwlink/?LinkId=733558
|
||||
// for the documentation about the tasks.json format
|
||||
"version": "2.0.0",
|
||||
"tasks": [
|
||||
{
|
||||
"label": "build",
|
||||
"command": "dotnet",
|
||||
"type": "shell",
|
||||
"args": [
|
||||
"build",
|
||||
// Ask dotnet build to generate full paths for file names.
|
||||
"/property:GenerateFullPaths=true",
|
||||
// Do not generate summary otherwise it leads to duplicate errors in Problems panel
|
||||
"/consoleloggerparameters:NoSummary"
|
||||
],
|
||||
"group": "build",
|
||||
"presentation": {
|
||||
"reveal": "silent"
|
||||
},
|
||||
"problemMatcher": "$msCompile"
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -1,14 +0,0 @@
|
||||
namespace SabreTools.Serialization
|
||||
{
|
||||
/// <summary>
|
||||
/// Separated value serializer/deserializer for AttractMode romlists
|
||||
/// </summary>
|
||||
public static class AttractMode
|
||||
{
|
||||
public const string HeaderWithoutRomname = "#Name;Title;Emulator;CloneOf;Year;Manufacturer;Category;Players;Rotation;Control;Status;DisplayCount;DisplayType;AltRomname;AltTitle;Extra;Buttons";
|
||||
public const int HeaderWithoutRomnameCount = 17;
|
||||
|
||||
public const string HeaderWithRomname = "#Romname;Title;Emulator;Cloneof;Year;Manufacturer;Category;Players;Rotation;Control;Status;DisplayCount;DisplayType;AltRomname;AltTitle;Extra;Buttons;Favourite;Tags;PlayedCount;PlayedTime;FileIsAvailable";
|
||||
public const int HeaderWithRomnameCount = 22;
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.AACS;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class AACS : IByteSerializer<MediaKeyBlock>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MediaKeyBlock Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public MediaKeyBlock? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.AACS().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.BDPlus;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class BDPlus : IByteSerializer<SVM>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public SVM Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public SVM? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.BDPlus().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.BFPK;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class BFPK : IByteSerializer<Archive>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Archive Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Archive? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.BFPK().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class BSP : IByteSerializer<Models.BSP.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.BSP.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.BSP.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.BSP().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.CFB;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class CFB : IByteSerializer<Binary>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Binary Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Binary? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.CFB().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class CIA : IByteSerializer<Models.N3DS.CIA>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.N3DS.CIA Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.N3DS.CIA? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.CIA().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class GCF : IByteSerializer<Models.GCF.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.GCF.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.GCF.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.GCF().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,30 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.InstallShieldCabinet;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
// TODO: Add multi-cabinet reading
|
||||
public partial class InstallShieldCabinet : IByteSerializer<Cabinet>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Cabinet Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Cabinet? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.InstallShieldCabinet().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.LinearExecutable;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class LinearExecutable : IByteSerializer<Executable>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Executable Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Executable? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.LinearExecutable().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.MSDOS;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class MSDOS : IByteSerializer<Executable>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Executable Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Executable? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.MSDOS().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,30 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.MicrosoftCabinet;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
// TODO: Add multi-cabinet reading
|
||||
public partial class MicrosoftCabinet : IByteSerializer<Cabinet>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Cabinet Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Cabinet? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.MicrosoftCabinet().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.MoPaQ;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class MoPaQ : IByteSerializer<Archive>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Archive Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Archive? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.MoPaQ().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.N3DS;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class N3DS : IByteSerializer<Cart>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Cart Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Cart? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.N3DS().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class NCF : IByteSerializer<Models.NCF.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.NCF.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.NCF.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.NCF().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.NewExecutable;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class NewExecutable : IByteSerializer<Executable>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Executable Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Executable? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.NewExecutable().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.Nitro;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class Nitro : IByteSerializer<Cart>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Cart Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Cart? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.Nitro().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class PAK : IByteSerializer<Models.PAK.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.PAK.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.PAK.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.PAK().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.PFF;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class PFF : IByteSerializer<Archive>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Archive Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Archive? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.PFF().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.PlayJ;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class PlayJAudio : IByteSerializer<AudioFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public AudioFile Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public AudioFile? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.PlayJAudio().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.PlayJ;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class PlayJPlaylist : IByteSerializer<Playlist>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Playlist Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Playlist? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.PlayJPlaylist().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.PortableExecutable;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class PortableExecutable : IByteSerializer<Executable>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Executable Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Executable? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.PortableExecutable().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,29 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.Quantum;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class Quantum : IByteSerializer<Archive>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Archive Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Archive? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.Quantum().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class SGA : IByteSerializer<Models.SGA.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.SGA.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.SGA.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.SGA().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class VBSP : IByteSerializer<Models.VBSP.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.VBSP.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.VBSP.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.VBSP().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class VPK : IByteSerializer<Models.VPK.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.VPK.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.VPK.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.VPK().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class WAD : IByteSerializer<Models.WAD.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.WAD.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.WAD.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.WAD().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Bytes
|
||||
{
|
||||
public partial class XZP : IByteSerializer<Models.XZP.File>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.XZP.File Deserialize(byte[] data, int offset)
|
||||
#else
|
||||
public Models.XZP.File? Deserialize(byte[]? data, int offset)
|
||||
#endif
|
||||
{
|
||||
// If the data is invalid
|
||||
if (data == null)
|
||||
return null;
|
||||
|
||||
// If the offset is out of bounds
|
||||
if (offset < 0 || offset >= data.Length)
|
||||
return null;
|
||||
|
||||
// Create a memory stream and parse that
|
||||
MemoryStream dataStream = new MemoryStream(data, offset, data.Length - offset);
|
||||
return new Streams.XZP().Deserialize(dataStream);
|
||||
}
|
||||
}
|
||||
}
|
||||
13
Enums.cs
13
Enums.cs
@@ -1,13 +0,0 @@
|
||||
namespace SabreTools.Serialization
|
||||
{
|
||||
public enum Hash
|
||||
{
|
||||
CRC,
|
||||
MD5,
|
||||
SHA1,
|
||||
SHA256,
|
||||
SHA384,
|
||||
SHA512,
|
||||
SpamSum,
|
||||
}
|
||||
}
|
||||
73
ExtractionTool/ExtractionTool.csproj
Normal file
73
ExtractionTool/ExtractionTool.csproj
Normal file
@@ -0,0 +1,73 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net20;net35;net40;net452;net462;net472;net48;netcoreapp3.1;net5.0;net6.0;net7.0;net8.0;net9.0</TargetFrameworks>
|
||||
<OutputType>Exe</OutputType>
|
||||
<CheckEolTargetFramework>false</CheckEolTargetFramework>
|
||||
<IncludeNativeLibrariesForSelfExtract>true</IncludeNativeLibrariesForSelfExtract>
|
||||
<IncludeSourceRevisionInInformationalVersion>false</IncludeSourceRevisionInInformationalVersion>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<Nullable>enable</Nullable>
|
||||
<SuppressTfmSupportBuildWarnings>true</SuppressTfmSupportBuildWarnings>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
<Version>1.9.2</Version>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Support All Frameworks -->
|
||||
<PropertyGroup Condition="$(TargetFramework.StartsWith(`net2`)) OR $(TargetFramework.StartsWith(`net3`)) OR $(TargetFramework.StartsWith(`net4`))">
|
||||
<RuntimeIdentifiers>win-x86;win-x64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="$(TargetFramework.StartsWith(`netcoreapp`)) OR $(TargetFramework.StartsWith(`net5`))">
|
||||
<RuntimeIdentifiers>win-x86;win-x64;win-arm64;linux-x64;linux-arm64;osx-x64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="$(TargetFramework.StartsWith(`net6`)) OR $(TargetFramework.StartsWith(`net7`)) OR $(TargetFramework.StartsWith(`net8`)) OR $(TargetFramework.StartsWith(`net9`))">
|
||||
<RuntimeIdentifiers>win-x86;win-x64;win-arm64;linux-x64;linux-arm64;osx-x64;osx-arm64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="$(RuntimeIdentifier.StartsWith(`osx-arm`))">
|
||||
<TargetFrameworks>net6.0;net7.0;net8.0;net9.0</TargetFrameworks>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Set a build flag for Windows specifically -->
|
||||
<PropertyGroup Condition="'$(RuntimeIdentifier)'=='win-x86'">
|
||||
<DefineConstants>$(DefineConstants);WINX86</DefineConstants>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(RuntimeIdentifier)'=='win-x64'">
|
||||
<DefineConstants>$(DefineConstants);WINX64</DefineConstants>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- These are needed for dealing with native Windows DLLs -->
|
||||
<ItemGroup Condition="'$(RuntimeIdentifier)'=='win-x86'">
|
||||
<ContentWithTargetPath Include="..\SabreTools.Serialization\runtimes\win-x86\native\CascLib.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToPublishDirectory>Always</CopyToPublishDirectory>
|
||||
<TargetPath>CascLib.dll</TargetPath>
|
||||
</ContentWithTargetPath>
|
||||
<ContentWithTargetPath Include="..\SabreTools.Serialization\runtimes\win-x86\native\StormLib.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToPublishDirectory>Always</CopyToPublishDirectory>
|
||||
<TargetPath>StormLib.dll</TargetPath>
|
||||
</ContentWithTargetPath>
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition="'$(RuntimeIdentifier)'=='win-x64'">
|
||||
<ContentWithTargetPath Include="..\SabreTools.Serialization\runtimes\win-x64\native\CascLib.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToPublishDirectory>Always</CopyToPublishDirectory>
|
||||
<TargetPath>CascLib.dll</TargetPath>
|
||||
</ContentWithTargetPath>
|
||||
<ContentWithTargetPath Include="..\SabreTools.Serialization\runtimes\win-x64\native\StormLib.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
<CopyToPublishDirectory>Always</CopyToPublishDirectory>
|
||||
<TargetPath>StormLib.dll</TargetPath>
|
||||
</ContentWithTargetPath>
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\SabreTools.Serialization\SabreTools.Serialization.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="SabreTools.IO" Version="1.7.2" />
|
||||
<PackageReference Include="System.Text.Encoding.CodePages" Version="9.0.8" Condition="!$(TargetFramework.StartsWith(`net2`)) AND !$(TargetFramework.StartsWith(`net3`)) AND !$(TargetFramework.StartsWith(`net40`)) AND !$(TargetFramework.StartsWith(`net452`))" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
129
ExtractionTool/Options.cs
Normal file
129
ExtractionTool/Options.cs
Normal file
@@ -0,0 +1,129 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
|
||||
namespace ExtractionTool
|
||||
{
|
||||
/// <summary>
|
||||
/// Set of options for the test executable
|
||||
/// </summary>
|
||||
internal sealed class Options
|
||||
{
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Enable debug output for relevant operations
|
||||
/// </summary>
|
||||
public bool Debug { get; private set; } = false;
|
||||
|
||||
/// <summary>
|
||||
/// Set of input paths to use for operations
|
||||
/// </summary>
|
||||
public List<string> InputPaths { get; private set; } = [];
|
||||
|
||||
/// <summary>
|
||||
/// Output path for archive extraction
|
||||
/// </summary>
|
||||
public string OutputPath { get; private set; } = string.Empty;
|
||||
|
||||
#endregion
|
||||
|
||||
/// <summary>
|
||||
/// Parse commandline arguments into an Options object
|
||||
/// </summary>
|
||||
public static Options? ParseOptions(string[] args)
|
||||
{
|
||||
// If we have invalid arguments
|
||||
if (args == null || args.Length == 0)
|
||||
return null;
|
||||
|
||||
// Create an Options object
|
||||
var options = new Options();
|
||||
|
||||
// Parse the options and paths
|
||||
for (int index = 0; index < args.Length; index++)
|
||||
{
|
||||
string arg = args[index];
|
||||
switch (arg)
|
||||
{
|
||||
case "-?":
|
||||
case "-h":
|
||||
case "--help":
|
||||
return null;
|
||||
|
||||
case "-d":
|
||||
case "--debug":
|
||||
options.Debug = true;
|
||||
break;
|
||||
|
||||
case "-o":
|
||||
case "--outdir":
|
||||
options.OutputPath = index + 1 < args.Length ? args[++index] : string.Empty;
|
||||
break;
|
||||
|
||||
default:
|
||||
options.InputPaths.Add(arg);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Validate we have any input paths to work on
|
||||
if (options.InputPaths.Count == 0)
|
||||
{
|
||||
Console.WriteLine("At least one path is required!");
|
||||
return null;
|
||||
}
|
||||
|
||||
// Validate the output path
|
||||
bool validPath = ValidateExtractionPath(options);
|
||||
if (!validPath)
|
||||
return null;
|
||||
|
||||
return options;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Display help text
|
||||
/// </summary>
|
||||
public static void DisplayHelp()
|
||||
{
|
||||
Console.WriteLine("Extraction Tool");
|
||||
Console.WriteLine();
|
||||
Console.WriteLine("ExtractionTool.exe <options> file|directory ...");
|
||||
Console.WriteLine();
|
||||
Console.WriteLine("Options:");
|
||||
Console.WriteLine("-?, -h, --help Display this help text and quit");
|
||||
Console.WriteLine("-d, --debug Enable debug mode");
|
||||
Console.WriteLine("-o, --outdir [PATH] Set output path for extraction (required)");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate the extraction path
|
||||
/// </summary>
|
||||
private static bool ValidateExtractionPath(Options options)
|
||||
{
|
||||
// Null or empty output path
|
||||
if (string.IsNullOrEmpty(options.OutputPath))
|
||||
{
|
||||
Console.WriteLine("Output directory required for extraction!");
|
||||
Console.WriteLine();
|
||||
return false;
|
||||
}
|
||||
|
||||
// Malformed output path or invalid location
|
||||
try
|
||||
{
|
||||
options.OutputPath = Path.GetFullPath(options.OutputPath);
|
||||
Directory.CreateDirectory(options.OutputPath);
|
||||
}
|
||||
catch
|
||||
{
|
||||
Console.WriteLine("Output directory could not be created!");
|
||||
Console.WriteLine();
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
249
ExtractionTool/Program.cs
Normal file
249
ExtractionTool/Program.cs
Normal file
@@ -0,0 +1,249 @@
|
||||
using System;
|
||||
using System.IO;
|
||||
using SabreTools.IO.Extensions;
|
||||
using SabreTools.Serialization.Wrappers;
|
||||
|
||||
namespace ExtractionTool
|
||||
{
|
||||
class Program
|
||||
{
|
||||
static void Main(string[] args)
|
||||
{
|
||||
#if NET462_OR_GREATER || NETCOREAPP
|
||||
// Register the codepages
|
||||
System.Text.Encoding.RegisterProvider(System.Text.CodePagesEncodingProvider.Instance);
|
||||
#endif
|
||||
|
||||
// Get the options from the arguments
|
||||
var options = Options.ParseOptions(args);
|
||||
|
||||
// If we have an invalid state
|
||||
if (options == null)
|
||||
{
|
||||
Options.DisplayHelp();
|
||||
return;
|
||||
}
|
||||
|
||||
// Loop through the input paths
|
||||
foreach (string inputPath in options.InputPaths)
|
||||
{
|
||||
ExtractPath(inputPath, options.OutputPath, options.Debug);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Wrapper to extract data for a single path
|
||||
/// </summary>
|
||||
/// <param name="path">File or directory path</param>
|
||||
/// <param name="outputDirectory">Output directory path</param>
|
||||
/// <param name="includeDebug">Enable including debug information</param>
|
||||
private static void ExtractPath(string path, string outputDirectory, bool includeDebug)
|
||||
{
|
||||
// Normalize by getting the full path
|
||||
path = Path.GetFullPath(path);
|
||||
Console.WriteLine($"Checking possible path: {path}");
|
||||
|
||||
// Check if the file or directory exists
|
||||
if (File.Exists(path))
|
||||
{
|
||||
ExtractFile(path, outputDirectory, includeDebug);
|
||||
}
|
||||
else if (Directory.Exists(path))
|
||||
{
|
||||
foreach (string file in IOExtensions.SafeEnumerateFiles(path, "*", SearchOption.AllDirectories))
|
||||
{
|
||||
ExtractFile(file, outputDirectory, includeDebug);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Console.WriteLine($"{path} does not exist, skipping...");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Print information for a single file, if possible
|
||||
/// </summary>
|
||||
private static void ExtractFile(string file, string outputDirectory, bool includeDebug)
|
||||
{
|
||||
Console.WriteLine($"Attempting to extract all files from {file}");
|
||||
using Stream stream = File.Open(file, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
|
||||
|
||||
// Get the extension for certain checks
|
||||
string extension = Path.GetExtension(file).ToLower().TrimStart('.');
|
||||
|
||||
// Get the first 16 bytes for matching
|
||||
byte[] magic = new byte[16];
|
||||
try
|
||||
{
|
||||
int read = stream.Read(magic, 0, 16);
|
||||
stream.Seek(0, SeekOrigin.Begin);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
if (includeDebug) Console.Error.WriteLine(ex);
|
||||
return;
|
||||
}
|
||||
|
||||
// Get the file type
|
||||
WrapperType ft = WrapperFactory.GetFileType(magic, extension);
|
||||
var wrapper = WrapperFactory.CreateWrapper(ft, stream);
|
||||
|
||||
// Create the output directory
|
||||
Directory.CreateDirectory(outputDirectory);
|
||||
|
||||
// Print the preamble
|
||||
Console.WriteLine($"Attempting to extract from '{wrapper?.Description() ?? "UNKNOWN"}'");
|
||||
Console.WriteLine();
|
||||
|
||||
switch (wrapper)
|
||||
{
|
||||
// 7-zip
|
||||
case SevenZip sz:
|
||||
sz.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// BFPK archive
|
||||
case BFPK bfpk:
|
||||
bfpk.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// BSP
|
||||
case BSP bsp:
|
||||
bsp.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// bzip2
|
||||
case BZip2 bzip2:
|
||||
bzip2.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// CFB
|
||||
case CFB cfb:
|
||||
cfb.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// GCF
|
||||
case GCF gcf:
|
||||
gcf.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// gzip
|
||||
case GZip gzip:
|
||||
gzip.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// InstallShield Archive V3 (Z)
|
||||
case InstallShieldArchiveV3 isv3:
|
||||
isv3.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// IS-CAB archive
|
||||
case InstallShieldCabinet iscab:
|
||||
iscab.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// LZ-compressed file, KWAJ variant
|
||||
case LZKWAJ kwaj:
|
||||
kwaj.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// LZ-compressed file, QBasic variant
|
||||
case LZQBasic qbasic:
|
||||
qbasic.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// LZ-compressed file, SZDD variant
|
||||
case LZSZDD szdd:
|
||||
szdd.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// Microsoft Cabinet archive
|
||||
case MicrosoftCabinet mscab:
|
||||
mscab.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// MoPaQ (MPQ) archive
|
||||
case MoPaQ mpq:
|
||||
mpq.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// New Executable
|
||||
case NewExecutable nex:
|
||||
nex.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// PAK
|
||||
case PAK pak:
|
||||
pak.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// PFF
|
||||
case PFF pff:
|
||||
pff.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// PKZIP
|
||||
case PKZIP pkzip:
|
||||
pkzip.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// Portable Executable
|
||||
case PortableExecutable pex:
|
||||
pex.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// Quantum
|
||||
case Quantum quantum:
|
||||
quantum.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// RAR
|
||||
case RAR rar:
|
||||
rar.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// SGA
|
||||
case SGA sga:
|
||||
sga.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// Tape Archive
|
||||
case TapeArchive tar:
|
||||
tar.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// VBSP
|
||||
case VBSP vbsp:
|
||||
vbsp.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// VPK
|
||||
case VPK vpk:
|
||||
vpk.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// WAD3
|
||||
case WAD3 wad:
|
||||
wad.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// xz
|
||||
case XZ xz:
|
||||
xz.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// XZP
|
||||
case XZP xzp:
|
||||
xzp.Extract(outputDirectory, includeDebug);
|
||||
break;
|
||||
|
||||
// Everything else
|
||||
default:
|
||||
Console.WriteLine("Not a supported extractable file format, skipping...");
|
||||
Console.WriteLine();
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class ArchiveDotOrg : XmlFile<Models.ArchiveDotOrg.Files>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class ArchiveDotOrg : XmlFile<Models.ArchiveDotOrg.Files>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
using SabreTools.Models.AttractMode;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class AttractMode : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.AttractMode().Deserialize(stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,32 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.AttractMode;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class AttractMode : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.AttractMode().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using SabreTools.Models.ClrMamePro;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class ClrMamePro : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path) => Deserialize(path, true);
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path) => Deserialize(path, true);
|
||||
#endif
|
||||
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path, bool quotes)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path, bool quotes)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.ClrMamePro().Deserialize(stream, quotes);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,39 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Models.ClrMamePro;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class ClrMamePro : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path) => Serialize(obj, path, true);
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path) => Serialize(obj, path, true);
|
||||
#endif
|
||||
|
||||
/// <inheritdoc cref="Serialize(MetadataFile, string)"/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path, bool quotes)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path, bool quotes)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.ClrMamePro().Serialize(obj, quotes))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class CueSheet : IFileSerializer<Models.CueSheets.CueSheet>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(Models.CueSheets.CueSheet obj, string path)
|
||||
#else
|
||||
public bool Serialize(Models.CueSheets.CueSheet? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.CueSheet().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
using SabreTools.Models.DosCenter;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class DosCenter : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.DosCenter().Deserialize(stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
using SabreTools.Models.DosCenter;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class DosCenter : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.DosCenter().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
using SabreTools.Models.EverdriveSMDB;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class EverdriveSMDB : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.EverdriveSMDB().Deserialize(stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
using SabreTools.Models.EverdriveSMDB;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class EverdriveSMDB : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.EverdriveSMDB().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,27 +0,0 @@
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Hashfile : IFileSerializer<Models.Hashfile.Hashfile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.Hashfile.Hashfile Deserialize(string path) => Deserialize(path, Hash.CRC);
|
||||
#else
|
||||
public Models.Hashfile.Hashfile? Deserialize(string? path) => Deserialize(path, Hash.CRC);
|
||||
#endif
|
||||
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public Models.Hashfile.Hashfile Deserialize(string path, Hash hash)
|
||||
#else
|
||||
public Models.Hashfile.Hashfile? Deserialize(string? path, Hash hash)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.Hashfile().Deserialize(stream, hash);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,37 +0,0 @@
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Hashfile : IFileSerializer<Models.Hashfile.Hashfile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(Models.Hashfile.Hashfile obj, string path) => Serialize(obj, path, Hash.CRC);
|
||||
#else
|
||||
public bool Serialize(Models.Hashfile.Hashfile? obj, string? path) => Serialize(obj, path, Hash.CRC);
|
||||
#endif
|
||||
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(Models.Hashfile.Hashfile obj, string path, Hash hash)
|
||||
#else
|
||||
public bool Serialize(Models.Hashfile.Hashfile? obj, string? path, Hash hash)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.Hashfile().Serialize(obj, hash))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
using SabreTools.Models.Listrom;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Listrom : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.Listrom().Deserialize(stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
using SabreTools.Models.Listrom;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Listrom : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.Listrom().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Listxml : XmlFile<Models.Listxml.Mame>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Listxml : XmlFile<Models.Listxml.Mame>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Logiqx : XmlFile<Models.Logiqx.Datafile>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,11 +0,0 @@
|
||||
using SabreTools.Models.Logiqx;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class Logiqx : XmlFile<Datafile>
|
||||
{
|
||||
/// <inheritdoc cref="Serialize(Datafile, string, string?, string?, string?, string?)" />
|
||||
public bool SerializeToFileWithDocType(Datafile obj, string path)
|
||||
=> Serialize(obj, path, Serialization.Logiqx.DocTypeName, Serialization.Logiqx.DocTypePubId, Serialization.Logiqx.DocTypeSysId, Serialization.Logiqx.DocTypeSysId);
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class M1 : XmlFile<Models.Listxml.M1>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class M1 : XmlFile<Models.Listxml.M1>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class OfflineList : XmlFile<Models.OfflineList.Dat>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class OfflineList : XmlFile<Models.OfflineList.Dat>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class OpenMSX : XmlFile<Models.OpenMSX.SoftwareDb>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,11 +0,0 @@
|
||||
using SabreTools.Models.OpenMSX;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class OpenMSX : XmlFile<SoftwareDb>
|
||||
{
|
||||
/// <inheritdoc cref="Serialize(SoftwareDb, string, string?, string?, string?, string?)" />
|
||||
public bool SerializeToFileWithDocType(SoftwareDb obj, string path)
|
||||
=> Serialize(obj, path, Serialization.OpenMSX.DocTypeName, Serialization.OpenMSX.DocTypePubId, Serialization.OpenMSX.DocTypeSysId, Serialization.OpenMSX.DocTypeSysId);
|
||||
}
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
using SabreTools.Models.PIC;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class PIC : IFileSerializer<DiscInformation>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public DiscInformation Deserialize(string path)
|
||||
#else
|
||||
public DiscInformation? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.PIC().Deserialize(stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
using SabreTools.Models.PIC;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class PIC : IFileSerializer<DiscInformation>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(DiscInformation obj, string path)
|
||||
#else
|
||||
public bool Serialize(DiscInformation? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.PIC().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,21 +0,0 @@
|
||||
using SabreTools.Models.RomCenter;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class RomCenter : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.RomCenter().Deserialize(stream);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,31 +0,0 @@
|
||||
using SabreTools.Models.RomCenter;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class RomCenter : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.RomCenter().Serialize(obj))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
using SabreTools.Models.SeparatedValue;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class SeparatedValue : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path) => Deserialize(path, ',');
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path) => Deserialize(path, ',');
|
||||
#endif
|
||||
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public MetadataFile Deserialize(string path, char delim)
|
||||
#else
|
||||
public MetadataFile? Deserialize(string? path, char delim)
|
||||
#endif
|
||||
{
|
||||
using (var stream = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.SeparatedValue().Deserialize(stream, delim);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,38 +0,0 @@
|
||||
using SabreTools.Models.SeparatedValue;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class SeparatedValue : IFileSerializer<MetadataFile>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path) => Serialize(obj, path, ',');
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path) => Serialize(obj, path, ',');
|
||||
#endif
|
||||
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(MetadataFile obj, string path, char delim)
|
||||
#else
|
||||
public bool Serialize(MetadataFile? obj, string? path, char delim)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.SeparatedValue().Serialize(obj, delim))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = System.IO.File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,7 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class SoftwareList : XmlFile<Models.SoftwareList.SoftwareList>
|
||||
{
|
||||
// All serialization logic is in the base class
|
||||
}
|
||||
}
|
||||
@@ -1,9 +0,0 @@
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class SoftwareList : XmlFile<Models.SoftwareList.SoftwareList>
|
||||
{
|
||||
/// <inheritdoc cref="SerializeToFile(Models.SoftwareList.SoftwareList, string, string?, string?, string?, string?)" />
|
||||
public bool SerializeToFileWithDocType(Models.SoftwareList.SoftwareList obj, string path)
|
||||
=> Serialize(obj, path, Serialization.SoftawreList.DocTypeName, Serialization.SoftawreList.DocTypePubId, Serialization.SoftawreList.DocTypeSysId, Serialization.SoftawreList.DocTypeSysId);
|
||||
}
|
||||
}
|
||||
@@ -1,216 +0,0 @@
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class XMID : IFileSerializer<Models.Xbox.XMID>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
/// <remarks>This treats the input path like a parseable string</remarks>
|
||||
#if NET48
|
||||
public Models.Xbox.XMID Deserialize(string path)
|
||||
#else
|
||||
public Models.Xbox.XMID? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return null;
|
||||
|
||||
string xmid = path.TrimEnd('\0');
|
||||
if (string.IsNullOrWhiteSpace(xmid))
|
||||
return null;
|
||||
|
||||
return ParseXMID(xmid);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Parse an XGD2/3 XMID string
|
||||
/// </summary>
|
||||
/// <param name="xmidString">XMID string to attempt to parse</param>
|
||||
/// <returns>Filled XMID on success, null on error</returns>
|
||||
#if NET48
|
||||
private static Models.Xbox.XMID ParseXMID(string xmidString)
|
||||
#else
|
||||
private static Models.Xbox.XMID? ParseXMID(string? xmidString)
|
||||
#endif
|
||||
{
|
||||
if (xmidString == null || xmidString.Length != 8)
|
||||
return null;
|
||||
|
||||
var xmid = new Models.Xbox.XMID();
|
||||
|
||||
xmid.PublisherIdentifier = xmidString.Substring(0, 2);
|
||||
if (string.IsNullOrEmpty(PublisherName(xmid)))
|
||||
return null;
|
||||
|
||||
xmid.GameID = xmidString.Substring(2, 3);
|
||||
xmid.VersionNumber = xmidString.Substring(5, 2);
|
||||
xmid.RegionIdentifier = xmidString[7];
|
||||
if (InternalRegion(xmid) == null)
|
||||
return null;
|
||||
|
||||
return xmid;
|
||||
}
|
||||
|
||||
#region Helpers
|
||||
|
||||
/// <summary>
|
||||
/// Human-readable name derived from the publisher identifier
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static string PublisherName(Models.Xbox.XMID xmid) => GetPublisher(xmid.PublisherIdentifier);
|
||||
#else
|
||||
public static string? PublisherName(Models.Xbox.XMID xmid) => GetPublisher(xmid.PublisherIdentifier);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Internally represented region
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static string InternalRegion(Models.Xbox.XMID xmid) => GetRegion(xmid.RegionIdentifier);
|
||||
#else
|
||||
public static string? InternalRegion(Models.Xbox.XMID xmid) => GetRegion(xmid.RegionIdentifier);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Get the full name of the publisher from the 2-character identifier
|
||||
/// </summary>
|
||||
/// <param name="publisherIdentifier">Case-sensitive 2-character identifier</param>
|
||||
/// <returns>Publisher name, if possible</returns>
|
||||
/// <see cref="https://xboxdevwiki.net/Xbe#Title_ID"/>
|
||||
#if NET48
|
||||
private static string GetPublisher(string publisherIdentifier)
|
||||
#else
|
||||
private static string? GetPublisher(string? publisherIdentifier)
|
||||
#endif
|
||||
{
|
||||
switch (publisherIdentifier)
|
||||
{
|
||||
case "AC": return "Acclaim Entertainment";
|
||||
case "AH": return "ARUSH Entertainment";
|
||||
case "AQ": return "Aqua System";
|
||||
case "AS": return "ASK";
|
||||
case "AT": return "Atlus";
|
||||
case "AV": return "Activision";
|
||||
case "AY": return "Aspyr Media";
|
||||
case "BA": return "Bandai";
|
||||
case "BL": return "Black Box";
|
||||
case "BM": return "BAM! Entertainment";
|
||||
case "BR": return "Broccoli Co.";
|
||||
case "BS": return "Bethesda Softworks";
|
||||
case "BU": return "Bunkasha Co.";
|
||||
case "BV": return "Buena Vista Games";
|
||||
case "BW": return "BBC Multimedia";
|
||||
case "BZ": return "Blizzard";
|
||||
case "CC": return "Capcom";
|
||||
case "CK": return "Kemco Corporation"; // TODO: Confirm
|
||||
case "CM": return "Codemasters";
|
||||
case "CV": return "Crave Entertainment";
|
||||
case "DC": return "DreamCatcher Interactive";
|
||||
case "DX": return "Davilex";
|
||||
case "EA": return "Electronic Arts (EA)";
|
||||
case "EC": return "Encore inc";
|
||||
case "EL": return "Enlight Software";
|
||||
case "EM": return "Empire Interactive";
|
||||
case "ES": return "Eidos Interactive";
|
||||
case "FI": return "Fox Interactive";
|
||||
case "FS": return "From Software";
|
||||
case "GE": return "Genki Co.";
|
||||
case "GV": return "Groove Games";
|
||||
case "HE": return "Tru Blu (Entertainment division of Home Entertainment Suppliers)";
|
||||
case "HP": return "Hip games";
|
||||
case "HU": return "Hudson Soft";
|
||||
case "HW": return "Highwaystar";
|
||||
case "IA": return "Mad Catz Interactive";
|
||||
case "IF": return "Idea Factory";
|
||||
case "IG": return "Infogrames";
|
||||
case "IL": return "Interlex Corporation";
|
||||
case "IM": return "Imagine Media";
|
||||
case "IO": return "Ignition Entertainment";
|
||||
case "IP": return "Interplay Entertainment";
|
||||
case "IX": return "InXile Entertainment"; // TODO: Confirm
|
||||
case "JA": return "Jaleco";
|
||||
case "JW": return "JoWooD";
|
||||
case "KB": return "Kemco"; // TODO: Confirm
|
||||
case "KI": return "Kids Station Inc."; // TODO: Confirm
|
||||
case "KN": return "Konami";
|
||||
case "KO": return "KOEI";
|
||||
case "KU": return "Kobi and / or GAE (formerly Global A Entertainment)"; // TODO: Confirm
|
||||
case "LA": return "LucasArts";
|
||||
case "LS": return "Black Bean Games (publishing arm of Leader S.p.A.)";
|
||||
case "MD": return "Metro3D";
|
||||
case "ME": return "Medix";
|
||||
case "MI": return "Microïds";
|
||||
case "MJ": return "Majesco Entertainment";
|
||||
case "MM": return "Myelin Media";
|
||||
case "MP": return "MediaQuest"; // TODO: Confirm
|
||||
case "MS": return "Microsoft Game Studios";
|
||||
case "MW": return "Midway Games";
|
||||
case "MX": return "Empire Interactive"; // TODO: Confirm
|
||||
case "NK": return "NewKidCo";
|
||||
case "NL": return "NovaLogic";
|
||||
case "NM": return "Namco";
|
||||
case "OX": return "Oxygen Interactive";
|
||||
case "PC": return "Playlogic Entertainment";
|
||||
case "PL": return "Phantagram Co., Ltd.";
|
||||
case "RA": return "Rage";
|
||||
case "SA": return "Sammy";
|
||||
case "SC": return "SCi Games";
|
||||
case "SE": return "SEGA";
|
||||
case "SN": return "SNK";
|
||||
case "SS": return "Simon & Schuster";
|
||||
case "SU": return "Success Corporation";
|
||||
case "SW": return "Swing! Deutschland";
|
||||
case "TA": return "Takara";
|
||||
case "TC": return "Tecmo";
|
||||
case "TD": return "The 3DO Company (or just 3DO)";
|
||||
case "TK": return "Takuyo";
|
||||
case "TM": return "TDK Mediactive";
|
||||
case "TQ": return "THQ";
|
||||
case "TS": return "Titus Interactive";
|
||||
case "TT": return "Take-Two Interactive Software";
|
||||
case "US": return "Ubisoft";
|
||||
case "VC": return "Victor Interactive Software";
|
||||
case "VN": return "Vivendi Universal (just took Interplays publishing rights)"; // TODO: Confirm
|
||||
case "VU": return "Vivendi Universal Games";
|
||||
case "VV": return "Vivendi Universal Games"; // TODO: Confirm
|
||||
case "WE": return "Wanadoo Edition";
|
||||
case "WR": return "Warner Bros. Interactive Entertainment"; // TODO: Confirm
|
||||
case "XI": return "XPEC Entertainment and Idea Factory";
|
||||
case "XK": return "Xbox kiosk disk?"; // TODO: Confirm
|
||||
case "XL": return "Xbox special bundled or live demo disk?"; // TODO: Confirm
|
||||
case "XM": return "Evolved Games"; // TODO: Confirm
|
||||
case "XP": return "XPEC Entertainment";
|
||||
case "XR": return "Panorama";
|
||||
case "YB": return "YBM Sisa (South-Korea)";
|
||||
case "ZD": return "Zushi Games (formerly Zoo Digital Publishing)";
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine the region based on the XGD serial character
|
||||
/// </summary>
|
||||
/// <param name="region">Character denoting the region</param>
|
||||
/// <returns>Region, if possible</returns>
|
||||
#if NET48
|
||||
private static string GetRegion(char region)
|
||||
#else
|
||||
private static string? GetRegion(char region)
|
||||
#endif
|
||||
{
|
||||
switch (region)
|
||||
{
|
||||
case 'W': return "World";
|
||||
case 'A': return "USA";
|
||||
case 'J': return "Japan / Asia";
|
||||
case 'E': return "Europe";
|
||||
case 'K': return "USA / Japan";
|
||||
case 'L': return "USA / Europe";
|
||||
case 'H': return "Japan / Europe";
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
using System;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class XMID : IFileSerializer<Models.Xbox.XMID>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(Models.Xbox.XMID obj, string path) => throw new NotImplementedException();
|
||||
#else
|
||||
public bool Serialize(Models.Xbox.XMID? obj, string? path) => throw new NotImplementedException();
|
||||
#endif
|
||||
}
|
||||
}
|
||||
@@ -1,275 +0,0 @@
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class XeMID : IFileSerializer<Models.Xbox.XeMID>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
/// <remarks>This treats the input path like a parseable string</remarks>
|
||||
#if NET48
|
||||
public Models.Xbox.XeMID Deserialize(string path)
|
||||
#else
|
||||
public Models.Xbox.XeMID? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return null;
|
||||
|
||||
string xemid = path.TrimEnd('\0');
|
||||
if (string.IsNullOrWhiteSpace(xemid))
|
||||
return null;
|
||||
|
||||
return ParseXeMID(xemid);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Parse an XGD2/3 XeMID string
|
||||
/// </summary>
|
||||
/// <param name="xemidString">XeMID string to attempt to parse</param>
|
||||
/// <returns>Filled XeMID on success, null on error</returns>
|
||||
#if NET48
|
||||
private static Models.Xbox.XeMID ParseXeMID(string xemidString)
|
||||
#else
|
||||
private static Models.Xbox.XeMID? ParseXeMID(string? xemidString)
|
||||
#endif
|
||||
{
|
||||
if (xemidString == null
|
||||
|| (xemidString.Length != 13 && xemidString.Length != 14
|
||||
&& xemidString.Length != 21 && xemidString.Length != 22))
|
||||
return null;
|
||||
|
||||
var xemid = new Models.Xbox.XeMID();
|
||||
|
||||
xemid.PublisherIdentifier = xemidString.Substring(0, 2);
|
||||
if (string.IsNullOrEmpty(PublisherName(xemid)))
|
||||
return null;
|
||||
|
||||
xemid.PlatformIdentifier = xemidString[2];
|
||||
if (xemid.PlatformIdentifier != '2')
|
||||
return null;
|
||||
|
||||
xemid.GameID = xemidString.Substring(3, 3);
|
||||
xemid.SKU = xemidString.Substring(6, 2);
|
||||
xemid.RegionIdentifier = xemidString[8];
|
||||
if (InternalRegion(xemid) == null)
|
||||
return null;
|
||||
|
||||
if (xemidString.Length == 13 || xemidString.Length == 21)
|
||||
{
|
||||
xemid.BaseVersion = xemidString.Substring(9, 1);
|
||||
xemid.MediaSubtypeIdentifier = xemidString[10];
|
||||
if (string.IsNullOrEmpty(MediaSubtype(xemid)))
|
||||
return null;
|
||||
|
||||
xemid.DiscNumberIdentifier = xemidString.Substring(11, 2);
|
||||
}
|
||||
else if (xemidString.Length == 14 || xemidString.Length == 22)
|
||||
{
|
||||
xemid.BaseVersion = xemidString.Substring(9, 2);
|
||||
xemid.MediaSubtypeIdentifier = xemidString[11];
|
||||
if (string.IsNullOrEmpty(MediaSubtype(xemid)))
|
||||
return null;
|
||||
|
||||
xemid.DiscNumberIdentifier = xemidString.Substring(12, 2);
|
||||
}
|
||||
|
||||
if (xemidString.Length == 21)
|
||||
xemid.CertificationSubmissionIdentifier = xemidString.Substring(13);
|
||||
else if (xemidString.Length == 22)
|
||||
xemid.CertificationSubmissionIdentifier = xemidString.Substring(14);
|
||||
|
||||
return xemid;
|
||||
}
|
||||
|
||||
#region Helpers
|
||||
|
||||
/// <summary>
|
||||
/// Human-readable name derived from the publisher identifier
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static string PublisherName(Models.Xbox.XeMID xemid) => GetPublisher(xemid.PublisherIdentifier);
|
||||
#else
|
||||
public static string? PublisherName(Models.Xbox.XeMID xemid) => GetPublisher(xemid.PublisherIdentifier);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Internally represented region
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static string InternalRegion(Models.Xbox.XeMID xemid) => GetRegion(xemid.RegionIdentifier);
|
||||
#else
|
||||
public static string? InternalRegion(Models.Xbox.XeMID xemid) => GetRegion(xemid.RegionIdentifier);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Human-readable subtype derived from the media identifier
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static string MediaSubtype(Models.Xbox.XeMID xemid) => GetMediaSubtype(xemid.MediaSubtypeIdentifier);
|
||||
#else
|
||||
public static string? MediaSubtype(Models.Xbox.XeMID xemid) => GetMediaSubtype(xemid.MediaSubtypeIdentifier);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Determine the XGD type based on the XGD2/3 media type identifier character
|
||||
/// </summary>
|
||||
/// <param name="mediaTypeIdentifier">Character denoting the media type</param>
|
||||
/// <returns>Media subtype as a string, if possible</returns>
|
||||
#if NET48
|
||||
private static string GetMediaSubtype(char mediaTypeIdentifier)
|
||||
#else
|
||||
private static string? GetMediaSubtype(char mediaTypeIdentifier)
|
||||
#endif
|
||||
{
|
||||
switch (mediaTypeIdentifier)
|
||||
{
|
||||
case 'F': return "XGD3";
|
||||
case 'X': return "XGD2";
|
||||
case 'Z': return "Games on Demand / Marketplace Demo";
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Get the full name of the publisher from the 2-character identifier
|
||||
/// </summary>
|
||||
/// <param name="publisherIdentifier">Case-sensitive 2-character identifier</param>
|
||||
/// <returns>Publisher name, if possible</returns>
|
||||
/// <see cref="https://xboxdevwiki.net/Xbe#Title_ID"/>
|
||||
#if NET48
|
||||
private static string GetPublisher(string publisherIdentifier)
|
||||
#else
|
||||
private static string? GetPublisher(string? publisherIdentifier)
|
||||
#endif
|
||||
{
|
||||
switch (publisherIdentifier)
|
||||
{
|
||||
case "AC": return "Acclaim Entertainment";
|
||||
case "AH": return "ARUSH Entertainment";
|
||||
case "AQ": return "Aqua System";
|
||||
case "AS": return "ASK";
|
||||
case "AT": return "Atlus";
|
||||
case "AV": return "Activision";
|
||||
case "AY": return "Aspyr Media";
|
||||
case "BA": return "Bandai";
|
||||
case "BL": return "Black Box";
|
||||
case "BM": return "BAM! Entertainment";
|
||||
case "BR": return "Broccoli Co.";
|
||||
case "BS": return "Bethesda Softworks";
|
||||
case "BU": return "Bunkasha Co.";
|
||||
case "BV": return "Buena Vista Games";
|
||||
case "BW": return "BBC Multimedia";
|
||||
case "BZ": return "Blizzard";
|
||||
case "CC": return "Capcom";
|
||||
case "CK": return "Kemco Corporation"; // TODO: Confirm
|
||||
case "CM": return "Codemasters";
|
||||
case "CV": return "Crave Entertainment";
|
||||
case "DC": return "DreamCatcher Interactive";
|
||||
case "DX": return "Davilex";
|
||||
case "EA": return "Electronic Arts (EA)";
|
||||
case "EC": return "Encore inc";
|
||||
case "EL": return "Enlight Software";
|
||||
case "EM": return "Empire Interactive";
|
||||
case "ES": return "Eidos Interactive";
|
||||
case "FI": return "Fox Interactive";
|
||||
case "FS": return "From Software";
|
||||
case "GE": return "Genki Co.";
|
||||
case "GV": return "Groove Games";
|
||||
case "HE": return "Tru Blu (Entertainment division of Home Entertainment Suppliers)";
|
||||
case "HP": return "Hip games";
|
||||
case "HU": return "Hudson Soft";
|
||||
case "HW": return "Highwaystar";
|
||||
case "IA": return "Mad Catz Interactive";
|
||||
case "IF": return "Idea Factory";
|
||||
case "IG": return "Infogrames";
|
||||
case "IL": return "Interlex Corporation";
|
||||
case "IM": return "Imagine Media";
|
||||
case "IO": return "Ignition Entertainment";
|
||||
case "IP": return "Interplay Entertainment";
|
||||
case "IX": return "InXile Entertainment"; // TODO: Confirm
|
||||
case "JA": return "Jaleco";
|
||||
case "JW": return "JoWooD";
|
||||
case "KB": return "Kemco"; // TODO: Confirm
|
||||
case "KI": return "Kids Station Inc."; // TODO: Confirm
|
||||
case "KN": return "Konami";
|
||||
case "KO": return "KOEI";
|
||||
case "KU": return "Kobi and / or GAE (formerly Global A Entertainment)"; // TODO: Confirm
|
||||
case "LA": return "LucasArts";
|
||||
case "LS": return "Black Bean Games (publishing arm of Leader S.p.A.)";
|
||||
case "MD": return "Metro3D";
|
||||
case "ME": return "Medix";
|
||||
case "MI": return "Microïds";
|
||||
case "MJ": return "Majesco Entertainment";
|
||||
case "MM": return "Myelin Media";
|
||||
case "MP": return "MediaQuest"; // TODO: Confirm
|
||||
case "MS": return "Microsoft Game Studios";
|
||||
case "MW": return "Midway Games";
|
||||
case "MX": return "Empire Interactive"; // TODO: Confirm
|
||||
case "NK": return "NewKidCo";
|
||||
case "NL": return "NovaLogic";
|
||||
case "NM": return "Namco";
|
||||
case "OX": return "Oxygen Interactive";
|
||||
case "PC": return "Playlogic Entertainment";
|
||||
case "PL": return "Phantagram Co., Ltd.";
|
||||
case "RA": return "Rage";
|
||||
case "SA": return "Sammy";
|
||||
case "SC": return "SCi Games";
|
||||
case "SE": return "SEGA";
|
||||
case "SN": return "SNK";
|
||||
case "SS": return "Simon & Schuster";
|
||||
case "SU": return "Success Corporation";
|
||||
case "SW": return "Swing! Deutschland";
|
||||
case "TA": return "Takara";
|
||||
case "TC": return "Tecmo";
|
||||
case "TD": return "The 3DO Company (or just 3DO)";
|
||||
case "TK": return "Takuyo";
|
||||
case "TM": return "TDK Mediactive";
|
||||
case "TQ": return "THQ";
|
||||
case "TS": return "Titus Interactive";
|
||||
case "TT": return "Take-Two Interactive Software";
|
||||
case "US": return "Ubisoft";
|
||||
case "VC": return "Victor Interactive Software";
|
||||
case "VN": return "Vivendi Universal (just took Interplays publishing rights)"; // TODO: Confirm
|
||||
case "VU": return "Vivendi Universal Games";
|
||||
case "VV": return "Vivendi Universal Games"; // TODO: Confirm
|
||||
case "WE": return "Wanadoo Edition";
|
||||
case "WR": return "Warner Bros. Interactive Entertainment"; // TODO: Confirm
|
||||
case "XI": return "XPEC Entertainment and Idea Factory";
|
||||
case "XK": return "Xbox kiosk disk?"; // TODO: Confirm
|
||||
case "XL": return "Xbox special bundled or live demo disk?"; // TODO: Confirm
|
||||
case "XM": return "Evolved Games"; // TODO: Confirm
|
||||
case "XP": return "XPEC Entertainment";
|
||||
case "XR": return "Panorama";
|
||||
case "YB": return "YBM Sisa (South-Korea)";
|
||||
case "ZD": return "Zushi Games (formerly Zoo Digital Publishing)";
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Determine the region based on the XGD serial character
|
||||
/// </summary>
|
||||
/// <param name="region">Character denoting the region</param>
|
||||
/// <returns>Region, if possible</returns>
|
||||
#if NET48
|
||||
private static string GetRegion(char region)
|
||||
#else
|
||||
private static string? GetRegion(char region)
|
||||
#endif
|
||||
{
|
||||
switch (region)
|
||||
{
|
||||
case 'W': return "World";
|
||||
case 'A': return "USA";
|
||||
case 'J': return "Japan / Asia";
|
||||
case 'E': return "Europe";
|
||||
case 'K': return "USA / Japan";
|
||||
case 'L': return "USA / Europe";
|
||||
case 'H': return "Japan / Europe";
|
||||
default: return null;
|
||||
}
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
}
|
||||
@@ -1,15 +0,0 @@
|
||||
using System;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
public partial class XeMID : IFileSerializer<Models.Xbox.XeMID>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(Models.Xbox.XeMID obj, string path) => throw new NotImplementedException();
|
||||
#else
|
||||
public bool Serialize(Models.Xbox.XeMID? obj, string? path) => throw new NotImplementedException();
|
||||
#endif
|
||||
}
|
||||
}
|
||||
@@ -1,24 +0,0 @@
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for other XML serializers
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public partial class XmlFile<T> : IFileSerializer<T>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public T Deserialize(string path)
|
||||
#else
|
||||
public T? Deserialize(string? path)
|
||||
#endif
|
||||
{
|
||||
using (var data = PathProcessor.OpenStream(path))
|
||||
{
|
||||
return new Streams.XmlFile<T>().Deserialize(data);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,54 +0,0 @@
|
||||
using System.IO;
|
||||
using SabreTools.Serialization.Interfaces;
|
||||
|
||||
namespace SabreTools.Serialization.Files
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for other XML serializers
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public partial class XmlFile<T> : IFileSerializer<T>
|
||||
{
|
||||
/// <inheritdoc/>
|
||||
#if NET48
|
||||
public bool Serialize(T obj, string path)
|
||||
#else
|
||||
public bool Serialize(T? obj, string? path)
|
||||
#endif
|
||||
=> Serialize(obj, path, null, null, null, null);
|
||||
|
||||
/// <summary>
|
||||
/// Serializes the defined type to an XML file
|
||||
/// </summary>
|
||||
/// <param name="obj">Data to serialize</param>
|
||||
/// <param name="path">Path to the file to serialize to</param>
|
||||
/// <param name="obj">Data to serialize</param>
|
||||
/// <param name="name">Optional DOCTYPE name</param>
|
||||
/// <param name="pubid">Optional DOCTYPE pubid</param>
|
||||
/// <param name="sysid">Optional DOCTYPE sysid</param>
|
||||
/// <param name="subset">Optional DOCTYPE name</param>
|
||||
/// <returns>True on successful serialization, false otherwise</returns>
|
||||
#if NET48
|
||||
public bool Serialize(T obj, string path, string name = null, string pubid = null, string sysid = null, string subset = null)
|
||||
#else
|
||||
public bool Serialize(T? obj, string? path, string? name = null, string? pubid = null, string? sysid = null, string? subset = null)
|
||||
#endif
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(path))
|
||||
return false;
|
||||
|
||||
using (var stream = new Streams.XmlFile<T>().Serialize(obj, name, pubid, sysid, subset))
|
||||
{
|
||||
if (stream == null)
|
||||
return false;
|
||||
|
||||
using (var fs = File.OpenWrite(path))
|
||||
{
|
||||
stream.CopyTo(fs);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
39
InfoPrint/InfoPrint.csproj
Normal file
39
InfoPrint/InfoPrint.csproj
Normal file
@@ -0,0 +1,39 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net20;net35;net40;net452;net462;net472;net48;netcoreapp3.1;net5.0;net6.0;net7.0;net8.0;net9.0</TargetFrameworks>
|
||||
<OutputType>Exe</OutputType>
|
||||
<CheckEolTargetFramework>false</CheckEolTargetFramework>
|
||||
<IncludeNativeLibrariesForSelfExtract>true</IncludeNativeLibrariesForSelfExtract>
|
||||
<IncludeSourceRevisionInInformationalVersion>false</IncludeSourceRevisionInInformationalVersion>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<Nullable>enable</Nullable>
|
||||
<SuppressTfmSupportBuildWarnings>true</SuppressTfmSupportBuildWarnings>
|
||||
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
|
||||
<Version>1.9.2</Version>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Support All Frameworks -->
|
||||
<PropertyGroup Condition="$(TargetFramework.StartsWith(`net2`)) OR $(TargetFramework.StartsWith(`net3`)) OR $(TargetFramework.StartsWith(`net4`))">
|
||||
<RuntimeIdentifiers>win-x86;win-x64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="$(TargetFramework.StartsWith(`netcoreapp`)) OR $(TargetFramework.StartsWith(`net5`))">
|
||||
<RuntimeIdentifiers>win-x86;win-x64;win-arm64;linux-x64;linux-arm64;osx-x64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="$(TargetFramework.StartsWith(`net6`)) OR $(TargetFramework.StartsWith(`net7`)) OR $(TargetFramework.StartsWith(`net8`)) OR $(TargetFramework.StartsWith(`net9`))">
|
||||
<RuntimeIdentifiers>win-x86;win-x64;win-arm64;linux-x64;linux-arm64;osx-x64;osx-arm64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="$(RuntimeIdentifier.StartsWith(`osx-arm`))">
|
||||
<TargetFrameworks>net6.0;net7.0;net8.0;net9.0</TargetFrameworks>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\SabreTools.Serialization\SabreTools.Serialization.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="SabreTools.IO" Version="1.7.2" />
|
||||
<PackageReference Include="SabreTools.Hashing" Version="1.5.0" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
141
InfoPrint/Options.cs
Normal file
141
InfoPrint/Options.cs
Normal file
@@ -0,0 +1,141 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace InfoPrint
|
||||
{
|
||||
/// <summary>
|
||||
/// Set of options for the test executable
|
||||
/// </summary>
|
||||
internal sealed class Options
|
||||
{
|
||||
#region Properties
|
||||
|
||||
/// <summary>
|
||||
/// Enable debug output for relevant operations
|
||||
/// </summary>
|
||||
public bool Debug { get; private set; } = false;
|
||||
|
||||
/// <summary>
|
||||
/// Output information to file only, skip printing to console
|
||||
/// </summary>
|
||||
public bool FileOnly { get; private set; } = false;
|
||||
|
||||
/// <summary>
|
||||
/// Print external file hashes
|
||||
/// </summary>
|
||||
public bool Hash { get; private set; } = false;
|
||||
|
||||
/// <summary>
|
||||
/// Set of input paths to use for operations
|
||||
/// </summary>
|
||||
public List<string> InputPaths { get; private set; } = [];
|
||||
|
||||
#if NETCOREAPP
|
||||
/// <summary>
|
||||
/// Enable JSON output
|
||||
/// </summary>
|
||||
public bool Json { get; private set; } = false;
|
||||
#endif
|
||||
|
||||
#endregion
|
||||
|
||||
/// <summary>
|
||||
/// Parse commandline arguments into an Options object
|
||||
/// </summary>
|
||||
public static Options? ParseOptions(string[] args)
|
||||
{
|
||||
// If we have invalid arguments
|
||||
if (args == null || args.Length == 0)
|
||||
return null;
|
||||
|
||||
// Create an Options object
|
||||
var options = new Options();
|
||||
|
||||
// Parse the features
|
||||
int index = 0;
|
||||
for (; index < args.Length; index++)
|
||||
{
|
||||
string arg = args[index];
|
||||
bool featureFound = false;
|
||||
switch (arg)
|
||||
{
|
||||
case "-?":
|
||||
case "-h":
|
||||
case "--help":
|
||||
return null;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
// If the flag wasn't a feature
|
||||
if (!featureFound)
|
||||
break;
|
||||
}
|
||||
|
||||
// Parse the options and paths
|
||||
for (; index < args.Length; index++)
|
||||
{
|
||||
string arg = args[index];
|
||||
switch (arg)
|
||||
{
|
||||
case "-d":
|
||||
case "--debug":
|
||||
options.Debug = true;
|
||||
break;
|
||||
|
||||
case "-c":
|
||||
case "--hash":
|
||||
options.Hash = true;
|
||||
break;
|
||||
|
||||
case "-f":
|
||||
case "--file":
|
||||
options.FileOnly = true;
|
||||
break;
|
||||
|
||||
case "-j":
|
||||
case "--json":
|
||||
#if NETCOREAPP
|
||||
options.Json = true;
|
||||
#else
|
||||
Console.WriteLine("JSON output not available in .NET Framework");
|
||||
#endif
|
||||
break;
|
||||
|
||||
default:
|
||||
options.InputPaths.Add(arg);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Validate we have any input paths to work on
|
||||
if (options.InputPaths.Count == 0)
|
||||
{
|
||||
Console.WriteLine("At least one path is required!");
|
||||
return null;
|
||||
}
|
||||
|
||||
return options;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Display help text
|
||||
/// </summary>
|
||||
public static void DisplayHelp()
|
||||
{
|
||||
Console.WriteLine("Information Printing Program");
|
||||
Console.WriteLine();
|
||||
Console.WriteLine("InfoPrint <options> file|directory ...");
|
||||
Console.WriteLine();
|
||||
Console.WriteLine("Options:");
|
||||
Console.WriteLine("-?, -h, --help Display this help text and quit");
|
||||
Console.WriteLine("-d, --debug Enable debug mode");
|
||||
Console.WriteLine("-c, --hash Output file hashes");
|
||||
Console.WriteLine("-f, --file Print to file only");
|
||||
#if NETCOREAPP
|
||||
Console.WriteLine("-j, --json Print info as JSON");
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
210
InfoPrint/Program.cs
Normal file
210
InfoPrint/Program.cs
Normal file
@@ -0,0 +1,210 @@
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Text;
|
||||
using SabreTools.Hashing;
|
||||
using SabreTools.IO.Extensions;
|
||||
using SabreTools.Serialization;
|
||||
using SabreTools.Serialization.Wrappers;
|
||||
|
||||
namespace InfoPrint
|
||||
{
|
||||
public static class Program
|
||||
{
|
||||
public static void Main(string[] args)
|
||||
{
|
||||
// Get the options from the arguments
|
||||
var options = Options.ParseOptions(args);
|
||||
|
||||
// If we have an invalid state
|
||||
if (options == null)
|
||||
{
|
||||
Options.DisplayHelp();
|
||||
return;
|
||||
}
|
||||
|
||||
// Loop through the input paths
|
||||
foreach (string inputPath in options.InputPaths)
|
||||
{
|
||||
PrintPathInfo(inputPath, options);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Wrapper to print information for a single path
|
||||
/// </summary>
|
||||
/// <param name="path">File or directory path</param>
|
||||
/// <param name="options">User-defined options</param>
|
||||
private static void PrintPathInfo(string path, Options options)
|
||||
{
|
||||
Console.WriteLine($"Checking possible path: {path}");
|
||||
|
||||
// Check if the file or directory exists
|
||||
if (File.Exists(path))
|
||||
{
|
||||
PrintFileInfo(path, options);
|
||||
}
|
||||
else if (Directory.Exists(path))
|
||||
{
|
||||
foreach (string file in IOExtensions.SafeEnumerateFiles(path, "*", SearchOption.AllDirectories))
|
||||
{
|
||||
PrintFileInfo(file, options);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
Console.WriteLine($"{path} does not exist, skipping...");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Print information for a single file, if possible
|
||||
/// </summary>
|
||||
/// <param name="file">File path</param>
|
||||
/// <param name="options">User-defined options</param>
|
||||
private static void PrintFileInfo(string file, Options options)
|
||||
{
|
||||
Console.WriteLine($"Attempting to print info for {file}");
|
||||
|
||||
// Get the base info output name
|
||||
string filenameBase = $"info-{DateTime.Now:yyyy-MM-dd_HHmmss.ffff}";
|
||||
|
||||
// If we have the hash flag
|
||||
if (options.Hash)
|
||||
{
|
||||
var hashBuilder = PrintHashInfo(file, options.Debug);
|
||||
if (hashBuilder != null)
|
||||
{
|
||||
// Create the output data
|
||||
string hashData = hashBuilder.ToString();
|
||||
|
||||
// Write the output data
|
||||
using var hsw = new StreamWriter(File.OpenWrite($"{filenameBase}.hashes"));
|
||||
hsw.WriteLine(hashData);
|
||||
hsw.Flush();
|
||||
}
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
using Stream stream = File.Open(file, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);
|
||||
|
||||
// Read the first 8 bytes
|
||||
byte[]? magic = stream.ReadBytes(8);
|
||||
stream.Seek(0, SeekOrigin.Begin);
|
||||
|
||||
// Get the file type
|
||||
string extension = Path.GetExtension(file).TrimStart('.');
|
||||
WrapperType ft = WrapperFactory.GetFileType(magic ?? [], extension);
|
||||
|
||||
// Print out the file format
|
||||
Console.WriteLine($"File format found: {ft}");
|
||||
|
||||
// Setup the wrapper to print
|
||||
var wrapper = WrapperFactory.CreateWrapper(ft, stream);
|
||||
|
||||
// If we don't have a wrapper
|
||||
if (wrapper == null)
|
||||
{
|
||||
Console.WriteLine($"Either {ft} is not supported or something went wrong during parsing!");
|
||||
Console.WriteLine();
|
||||
return;
|
||||
}
|
||||
|
||||
#if NETCOREAPP
|
||||
// If we have the JSON flag
|
||||
if (options.Json)
|
||||
{
|
||||
// Create the output data
|
||||
string serializedData = wrapper.ExportJSON();
|
||||
|
||||
// Write the output data
|
||||
using var jsw = new StreamWriter(File.OpenWrite($"{filenameBase}.json"));
|
||||
jsw.WriteLine(serializedData);
|
||||
jsw.Flush();
|
||||
}
|
||||
#endif
|
||||
|
||||
// Create the output data
|
||||
var builder = wrapper.ExportStringBuilder();
|
||||
if (builder == null)
|
||||
{
|
||||
Console.WriteLine("No item information could be generated");
|
||||
return;
|
||||
}
|
||||
|
||||
// Only print to console if enabled
|
||||
if (!options.FileOnly)
|
||||
Console.WriteLine(builder);
|
||||
|
||||
using var sw = new StreamWriter(File.OpenWrite($"{filenameBase}.txt"));
|
||||
sw.WriteLine(file);
|
||||
sw.WriteLine();
|
||||
sw.WriteLine(builder.ToString());
|
||||
sw.Flush();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine(options.Debug ? ex : "[Exception opening file, please try again]");
|
||||
Console.WriteLine();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Print hash information for a single file, if possible
|
||||
/// </summary>
|
||||
/// <param name="file">File path</param>
|
||||
/// <param name="debug">Enable debug output</param>
|
||||
/// <returns>StringBuilder representing the hash information, if possible</returns>
|
||||
private static StringBuilder? PrintHashInfo(string file, bool debug)
|
||||
{
|
||||
// Ignore missing files
|
||||
if (!File.Exists(file))
|
||||
return null;
|
||||
|
||||
Console.WriteLine($"Attempting to hash {file}, this may take a while...");
|
||||
|
||||
try
|
||||
{
|
||||
// Get all file hashes for flexibility
|
||||
var hashes = HashTool.GetFileHashes(file);
|
||||
if (hashes == null)
|
||||
{
|
||||
if (debug) Console.WriteLine($"Hashes for {file} could not be retrieved");
|
||||
return null;
|
||||
}
|
||||
|
||||
// Output subset of available hashes
|
||||
var builder = new StringBuilder();
|
||||
if (hashes.TryGetValue(HashType.CRC16, out string? crc16) && crc16 != null)
|
||||
builder.AppendLine($"CRC-16 checksum: {crc16}");
|
||||
if (hashes.TryGetValue(HashType.CRC32, out string? crc32) && crc32 != null)
|
||||
builder.AppendLine($"CRC-32 checksum: {crc32}");
|
||||
if (hashes.TryGetValue(HashType.MD2, out string? md2) && md2 != null)
|
||||
builder.AppendLine($"MD2 hash: {md2}");
|
||||
if (hashes.TryGetValue(HashType.MD4, out string? md4) && md4 != null)
|
||||
builder.AppendLine($"MD4 hash: {md4}");
|
||||
if (hashes.TryGetValue(HashType.MD5, out string? md5) && md5 != null)
|
||||
builder.AppendLine($"MD5 hash: {md5}");
|
||||
if (hashes.TryGetValue(HashType.RIPEMD128, out string? ripemd128) && ripemd128 != null)
|
||||
builder.AppendLine($"RIPEMD-128 hash: {ripemd128}");
|
||||
if (hashes.TryGetValue(HashType.RIPEMD160, out string? ripemd160) && ripemd160 != null)
|
||||
builder.AppendLine($"RIPEMD-160 hash: {ripemd160}");
|
||||
if (hashes.TryGetValue(HashType.SHA1, out string? sha1) && sha1 != null)
|
||||
builder.AppendLine($"SHA-1 hash: {sha1}");
|
||||
if (hashes.TryGetValue(HashType.SHA256, out string? sha256) && sha256 != null)
|
||||
builder.AppendLine($"SHA-256 hash: {sha256}");
|
||||
if (hashes.TryGetValue(HashType.SHA384, out string? sha384) && sha384 != null)
|
||||
builder.AppendLine($"SHA-384 hash: {sha384}");
|
||||
if (hashes.TryGetValue(HashType.SHA512, out string? sha512) && sha512 != null)
|
||||
builder.AppendLine($"SHA-512 hash: {sha512}");
|
||||
|
||||
return builder;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
Console.WriteLine(debug ? ex : "[Exception opening file, please try again]");
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,33 +0,0 @@
|
||||
namespace SabreTools.Serialization.Interfaces
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines how to serialize to and from files
|
||||
/// </summary>
|
||||
public interface IFileSerializer<T>
|
||||
{
|
||||
/// <summary>
|
||||
/// Deserialize a file into <typeparamref name="T"/>
|
||||
/// </summary>
|
||||
/// <typeparam name="T">Type of object to deserialize to</typeparam>
|
||||
/// <param name="path">Path to deserialize from</param>
|
||||
/// <returns>Filled object on success, null on error</returns>
|
||||
#if NET48
|
||||
T Deserialize(string path);
|
||||
#else
|
||||
T? Deserialize(string? path);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Sserialize a <typeparamref name="T"/> into a file
|
||||
/// </summary>
|
||||
/// <typeparam name="T">Type of object to serialize from</typeparam>
|
||||
/// <param name="obj">Data to serialize</param>
|
||||
/// <param name="path">Path to the file to serialize to</param>
|
||||
/// <returns>True on successful serialization, false otherwise</returns>
|
||||
#if NET48
|
||||
bool Serialize(T obj, string path);
|
||||
#else
|
||||
bool Serialize(T? obj, string? path);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
@@ -1,34 +0,0 @@
|
||||
using System.IO;
|
||||
|
||||
namespace SabreTools.Serialization.Interfaces
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines how to serialize to and from Streams
|
||||
/// </summary>
|
||||
public interface IStreamSerializer<T>
|
||||
{
|
||||
/// <summary>
|
||||
/// Deserialize a Stream into <typeparamref name="T"/>
|
||||
/// </summary>
|
||||
/// <typeparam name="T">Type of object to deserialize to</typeparam>
|
||||
/// <param name="data">Stream to parse</param>
|
||||
/// <returns>Filled object on success, null on error</returns>
|
||||
#if NET48
|
||||
T Deserialize(Stream data);
|
||||
#else
|
||||
T? Deserialize(Stream? data);
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// Serialize a <typeparamref name="T"/> into a Stream
|
||||
/// </summary>
|
||||
/// <typeparam name="T">Type of object to serialize from</typeparam>
|
||||
/// <param name="obj">Data to serialize</param>
|
||||
/// <returns>Filled object on success, null on error</returns>
|
||||
#if NET48
|
||||
Stream Serialize(T obj);
|
||||
#else
|
||||
Stream? Serialize(T? obj);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
107
Internal.cs
107
Internal.cs
@@ -1,107 +0,0 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SabreTools.Models.Metadata;
|
||||
|
||||
namespace SabreTools.Serialization
|
||||
{
|
||||
public static class Internal
|
||||
{
|
||||
/// <summary>
|
||||
/// Extract nested items from a Dump
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static DatItem[] ExtractItems(Dump item)
|
||||
#else
|
||||
public static DatItem[]? ExtractItems(Dump? item)
|
||||
#endif
|
||||
{
|
||||
if (item == null)
|
||||
return null;
|
||||
|
||||
var datItems = new List<DatItem>();
|
||||
|
||||
var rom = item.Read<Rom>(Dump.RomKey);
|
||||
if (rom != null)
|
||||
datItems.Add(rom);
|
||||
|
||||
var megaRom = item.Read<Rom>(Dump.MegaRomKey);
|
||||
if (megaRom != null)
|
||||
datItems.Add(megaRom);
|
||||
|
||||
var sccPlusCart = item.Read<Rom>(Dump.SCCPlusCartKey);
|
||||
if (sccPlusCart != null)
|
||||
datItems.Add(sccPlusCart);
|
||||
|
||||
return datItems.ToArray();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Extract nested items from a Part
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public static DatItem[] ExtractItems(Part item)
|
||||
#else
|
||||
public static DatItem[]? ExtractItems(Part? item)
|
||||
#endif
|
||||
{
|
||||
if (item == null)
|
||||
return null;
|
||||
|
||||
var datItems = new List<DatItem>();
|
||||
|
||||
var features = item.Read<Feature[]>(Part.FeatureKey);
|
||||
if (features != null && features.Any())
|
||||
datItems.AddRange(features);
|
||||
|
||||
var dataAreas = item.Read<DataArea[]>(Part.DataAreaKey);
|
||||
if (dataAreas != null && dataAreas.Any())
|
||||
{
|
||||
datItems.AddRange(dataAreas
|
||||
.Where(d => d != null)
|
||||
.SelectMany(ExtractItems));
|
||||
}
|
||||
|
||||
var diskAreas = item.Read<DiskArea[]>(Part.DiskAreaKey);
|
||||
if (diskAreas != null && diskAreas.Any())
|
||||
{
|
||||
datItems.AddRange(diskAreas
|
||||
.Where(d => d != null)
|
||||
.SelectMany(ExtractItems));
|
||||
}
|
||||
|
||||
var dipSwitches = item.Read<DipSwitch[]>(Part.DipSwitchKey);
|
||||
if (dipSwitches != null && dipSwitches.Any())
|
||||
{
|
||||
datItems.AddRange(dipSwitches
|
||||
.Where(d => d != null));
|
||||
}
|
||||
|
||||
return datItems.ToArray();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Extract nested items from a DataArea
|
||||
/// </summary>
|
||||
private static Rom[] ExtractItems(DataArea item)
|
||||
{
|
||||
var roms = item.Read<Rom[]>(DataArea.RomKey);
|
||||
if (roms == null || !roms.Any())
|
||||
return Array.Empty<Rom>();
|
||||
|
||||
return roms.ToArray();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Extract nested items from a DiskArea
|
||||
/// </summary>
|
||||
private static Disk[] ExtractItems(DiskArea item)
|
||||
{
|
||||
var roms = item.Read<Disk[]>(DiskArea.DiskKey);
|
||||
if (roms == null || !roms.Any())
|
||||
return Array.Empty<Disk>();
|
||||
|
||||
return roms.ToArray();
|
||||
}
|
||||
}
|
||||
}
|
||||
7
LICENSE
Normal file
7
LICENSE
Normal file
@@ -0,0 +1,7 @@
|
||||
Copyright (c) 2018-2025 Matt Nadareski
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice (including the next paragraph) shall be included in all copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
32
Logiqx.cs
32
Logiqx.cs
@@ -1,32 +0,0 @@
|
||||
namespace SabreTools.Serialization
|
||||
{
|
||||
/// <summary>
|
||||
/// XML deserializer for Logiqx-derived metadata files
|
||||
/// </summary>
|
||||
public static class Logiqx
|
||||
{
|
||||
/// <summary>
|
||||
/// name field for DOCTYPE
|
||||
/// </summary>
|
||||
public const string DocTypeName = "datafile";
|
||||
|
||||
/// <summary>
|
||||
/// pubid field for DOCTYPE
|
||||
/// </summary>
|
||||
public const string DocTypePubId = "-//Logiqx//DTD ROM Management Datafile//EN";
|
||||
|
||||
/// <summary>
|
||||
/// sysid field for DOCTYPE
|
||||
/// </summary>
|
||||
public const string DocTypeSysId = "http://www.logiqx.com/Dats/datafile.dtd";
|
||||
|
||||
/// <summary>
|
||||
/// subset field for DOCTYPE
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public const string DocTypeSubset = null;
|
||||
#else
|
||||
public const string? DocTypeSubset = null;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
36
OpenMSX.cs
36
OpenMSX.cs
@@ -1,36 +0,0 @@
|
||||
namespace SabreTools.Serialization
|
||||
{
|
||||
/// <summary>
|
||||
/// XML deserializer for OpenMSX software database files
|
||||
/// </summary>
|
||||
public static class OpenMSX
|
||||
{
|
||||
/// <summary>
|
||||
/// name field for DOCTYPE
|
||||
/// </summary>
|
||||
public const string DocTypeName = "softwaredb";
|
||||
|
||||
/// <summary>
|
||||
/// pubid field for DOCTYPE
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public const string DocTypePubId = null;
|
||||
#else
|
||||
public const string? DocTypePubId = null;
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// sysid field for DOCTYPE
|
||||
/// </summary>
|
||||
public const string DocTypeSysId = "softwaredb1.dtd";
|
||||
|
||||
/// <summary>
|
||||
/// subset field for DOCTYPE
|
||||
/// </summary>
|
||||
#if NET48
|
||||
public const string DocTypeSubset = null;
|
||||
#else
|
||||
public const string? DocTypeSubset = null;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
@@ -1,54 +0,0 @@
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.IO.Compression;
|
||||
|
||||
namespace SabreTools.Serialization
|
||||
{
|
||||
internal class PathProcessor
|
||||
{
|
||||
/// <summary>
|
||||
/// Opens a path as a stream in a safe manner, decompressing if needed
|
||||
/// </summary>
|
||||
/// <param name="path">Path to open as a stream</param>
|
||||
/// <returns>Stream representing the file, null on error</returns>
|
||||
#if NET48
|
||||
public static Stream OpenStream(string path)
|
||||
#else
|
||||
public static Stream? OpenStream(string? path)
|
||||
#endif
|
||||
{
|
||||
try
|
||||
{
|
||||
// If we don't have a file
|
||||
if (string.IsNullOrWhiteSpace(path) || !File.Exists(path))
|
||||
return null;
|
||||
|
||||
// Open the file for deserialization
|
||||
var stream = File.OpenRead(path);
|
||||
|
||||
// Get the extension to determine if additional handling is needed
|
||||
string ext = Path.GetExtension(path).TrimStart('.');
|
||||
|
||||
// Determine what we do based on the extension
|
||||
if (string.Equals(ext, "gz", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
return new GZipStream(stream, CompressionMode.Decompress);
|
||||
}
|
||||
else if (string.Equals(ext, "zip", StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
// TODO: Support zip-compressed files
|
||||
return null;
|
||||
}
|
||||
else
|
||||
{
|
||||
return stream;
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
// TODO: Handle logging the exception
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
110
README.MD
110
README.MD
@@ -1,25 +1,115 @@
|
||||
# SabreTools.Serialization
|
||||
|
||||
[](https://github.com/SabreTools/SabreTools.Serialization/actions/workflows/build_and_test.yml)
|
||||
|
||||
This library comprises of serializers that both read and write from files and streams to the dedicated models as well as convert to and from the common internal models. This library is partially used by the current parsing and writing code but none of the internal model serialization is used.
|
||||
|
||||
Find the link to the Nuget package [here](https://www.nuget.org/packages/SabreTools.Serialization).
|
||||
|
||||
## `SabreTools.Serialization.Bytes`
|
||||
The following non-project libraries (or ports thereof) are used for file handling:
|
||||
|
||||
This namespace comprises of deserializers that take byte arrays to convert into models.
|
||||
- [SharpCompress](https://github.com/adamhathcock/sharpcompress) - Common archive format extraction
|
||||
- [StormLibSharp](https://github.com/robpaveza/stormlibsharp) - MoPaQ extraction [Unused in .NET Framework 2.0/3.5/4.0, non-Windows, and non-x86 builds due to Windows-specific libraries]
|
||||
|
||||
## `SabreTools.Serialization.CrossModel`
|
||||
The following projects have influenced this library:
|
||||
|
||||
This namespace comprises of serializers and deserializers that convert models to other common ones. This is mainly used for metadata files converting to and from a common, `Dictionary`-based model.
|
||||
- [libmspack](https://github.com/kyz/libmspack) - Documentation around the MS-CAB format and associated compression methods.
|
||||
- [Unshield](https://github.com/twogood/unshield/) - InstallShield CAB extraction tool that influenced internal handling
|
||||
|
||||
## `SabreTools.Serialization.Files`
|
||||
## Releases
|
||||
|
||||
This namespace comprises of serializers and deserializers that can convert to and from files on disk. Most of the serializers are symmetric, but this is not guaranteed. Unimplemented methods will throw `NotImplementedException`.
|
||||
For the most recent stable build, download the latest release here: [Releases Page](https://github.com/SabreTools/SabreTools.Serialization/releases)
|
||||
|
||||
## `SabreTools.Serialization.Streams`
|
||||
For the latest WIP build here: [Rolling Release](https://github.com/SabreTools/SabreTools.Serialization/releases/tag/rolling)
|
||||
|
||||
This namespace comprises of serializers and deserializers that can convert to and from any type of stream. Most of the serializers are symmetric, but this is not guaranteed. Unimplemented methods will throw `NotImplementedException`.
|
||||
## InfoPrint
|
||||
|
||||
## `SabreTools.Serialization.Wrappers`
|
||||
**InfoPrint** is a reference implementation for the deserialization and printing features of the library, packaged as a standalone executable for all supported platforms. It will attempt to detect and display information about many supported file types, optionally both hashing the file and outputting the information to a JSON file (.NET Core 3.1 and above only).
|
||||
|
||||
This namespace comrpises of wrapping classes that include keeping a reference to the source of each serializable model. Some of the wrappers may also include what are referred to as "extension properties", which are generated properties derived from either parts of the model or the underlying source.
|
||||
```
|
||||
InfoPrint <options> file|directory ...
|
||||
|
||||
Options:
|
||||
-?, -h, --help Display this help text and quit
|
||||
-d, --debug Enable debug mode
|
||||
-c, --hash Output file hashes
|
||||
-j, --json Print info as JSON
|
||||
```
|
||||
|
||||
## ExtractionTool
|
||||
|
||||
**ExtractionTool** is a reference implementation for the extraction features of the library, packaged as a standalone executable for all supported platforms. It will attempt to detect and extract many supported file types. See the table below for supported extraction functionality.
|
||||
|
||||
```
|
||||
ExtractionTool.exe <options> file|directory ...
|
||||
|
||||
Options:
|
||||
-?, -h, --help Display this help text and quit
|
||||
-d, --debug Enable debug mode
|
||||
-o, --outdir [PATH] Set output path for extraction (required)
|
||||
```
|
||||
|
||||
| Format Name | Notes |
|
||||
| --- | --- |
|
||||
| 7-zip archive | .NET Framework 4.6.2 and greater |
|
||||
| BFPK custom archive format | |
|
||||
| bzip2 archive | .NET Framework 4.6.2 and greater |
|
||||
| Compound File Binary (CFB) | Only CFB common pieces extractable. .NET Framework 4.0 and greater |
|
||||
| gzip archive | |
|
||||
| Half-Life Game Cache File (GCF) | |
|
||||
| Half-Life Level (BSP) | |
|
||||
| Half-Life Package File (PAK) | |
|
||||
| Half-Life Texture Package File (WAD3) | |
|
||||
| Half-Life 2 Level (VBSP) | |
|
||||
| InstallShield Archive V3 (Z) | |
|
||||
| InstallShield CAB | |
|
||||
| Microsoft cabinet file | Does not support LZX or Quantum compression |
|
||||
| Microsoft LZ-compressed files | KWAJ, QBasic, and SZDD variants |
|
||||
| MoPaQ game data archive (MPQ) | Currently not working. Windows only. .NET Framework 4.5.2 and above |
|
||||
| New Exectuable | Embedded archives and executables in the overlay and Wise installer |
|
||||
| NovaLogic Game Archive Format (PFF) | |
|
||||
| PKZIP and derived files (ZIP, etc.) | .NET Framework 4.6.2 and greater |
|
||||
| Portable Executable | Embedded archives and executables in the resources and overlay, CExe-packed data, SFX archives (7-zip, PKZIP, and RAR), and Wise installer |
|
||||
| Quantum archive (Q) | Currently not working |
|
||||
| RAR archive (RAR) | .NET Framework 4.6.2 and greater |
|
||||
| SGA game archive | |
|
||||
| Tape archive (TAR) | |
|
||||
| Valve Package File (VPK) | |
|
||||
| XBox Package File (XZP) | |
|
||||
| xz archive (XZ) | .NET Framework 4.6.2 and greater |
|
||||
|
||||
## Interfaces
|
||||
|
||||
Below is a table representing the various conversion interfaces that are implemented within this library.
|
||||
|
||||
| Interface Name | Source Type | Destination Type |
|
||||
| --- | --- | --- |
|
||||
| `IByteDeserializer` | `byte[]?` | Model |
|
||||
| `IByteSerializer` | Model | `byte[]?` |
|
||||
| `IFileDeserializer` | `string?` path | Model |
|
||||
| `IFileSerializer` | Model | `string?` path |
|
||||
| `IModelSerializer` | Model | Model |
|
||||
| `IStreamDeserializer` | `Stream?` | Model |
|
||||
| `IStreamSerializer` | Model | `Stream?` |
|
||||
| `IStringDeserializer` | `string?` representation | Model |
|
||||
| `IStringSerializer` | Model | `string?` representation |
|
||||
|
||||
Below is a table representing the various non-conversion interfaces that are implemented within this library.
|
||||
|
||||
| Interface Name | Purpose |
|
||||
| --- | --- |
|
||||
| `IExtractable` | Marks a wrapper as able to be extracted |
|
||||
| `IPrinter` | Provides a formatted output for a model |
|
||||
| `IWrapper` / `IWrapper<T>` | Wraps a model or set of models to provide additional functionality |
|
||||
|
||||
## Namespaces
|
||||
|
||||
Below is a table of all namespaces within the library and what they represent
|
||||
|
||||
| Namespace | Description |
|
||||
| --- | --- |
|
||||
| `SabreTools.Serialization.CrossModel` | Convert between models; mainly used for metadata files converting to and from a common, `Dictionary`-based model |
|
||||
| `SabreTools.Serialization.Deserializers` | Convert from external sources to models |
|
||||
| `SabreTools.Serialization.Printers` | Export model information in a formatted manner |
|
||||
| `SabreTools.Serialization.Serializers` | Convert from models to external sources |
|
||||
| `SabreTools.Serialization.Wrappers` | Classes that wrap serialization and models to allow for including extension properties |
|
||||
|
||||
173
SabreTools.Serialization.Test/CrossModel/ArchiveDotOrgTests.cs
Normal file
173
SabreTools.Serialization.Test/CrossModel/ArchiveDotOrgTests.cs
Normal file
@@ -0,0 +1,173 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class ArchiveDotOrgTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.ArchiveDotOrg();
|
||||
|
||||
// Build the data
|
||||
Models.ArchiveDotOrg.Files files = Build();
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(files);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.ArchiveDotOrg.Files? newFiles = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newFiles);
|
||||
Assert.NotNull(newFiles.File);
|
||||
var newFile = Assert.Single(newFiles.File);
|
||||
Validate(newFile);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.ArchiveDotOrg.Files Build()
|
||||
{
|
||||
var file = new Models.ArchiveDotOrg.File
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Source = "XXXXXX",
|
||||
BitTorrentMagnetHash = "XXXXXX",
|
||||
LastModifiedTime = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
CRC32 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
FileCount = "XXXXXX",
|
||||
Format = "XXXXXX",
|
||||
Original = "XXXXXX",
|
||||
Summation = "XXXXXX",
|
||||
MatrixNumber = "XXXXXX",
|
||||
CollectionCatalogNumber = "XXXXXX",
|
||||
Publisher = "XXXXXX",
|
||||
Comment = "XXXXXX",
|
||||
ASRDetectedLang = "XXXXXX",
|
||||
ASRDetectedLangConf = "XXXXXX",
|
||||
ASRTranscribedLang = "XXXXXX",
|
||||
WhisperASRModuleVersion = "XXXXXX",
|
||||
WhisperModelHash = "XXXXXX",
|
||||
WhisperModelName = "XXXXXX",
|
||||
WhisperVersion = "XXXXXX",
|
||||
ClothCoverDetectionModuleVersion = "XXXXXX",
|
||||
hOCRCharToWordhOCRVersion = "XXXXXX",
|
||||
hOCRCharToWordModuleVersion = "XXXXXX",
|
||||
hOCRFtsTexthOCRVersion = "XXXXXX",
|
||||
hOCRFtsTextModuleVersion = "XXXXXX",
|
||||
hOCRPageIndexhOCRVersion = "XXXXXX",
|
||||
hOCRPageIndexModuleVersion = "XXXXXX",
|
||||
TesseractOCR = "XXXXXX",
|
||||
TesseractOCRConverted = "XXXXXX",
|
||||
TesseractOCRDetectedLang = "XXXXXX",
|
||||
TesseractOCRDetectedLangConf = "XXXXXX",
|
||||
TesseractOCRDetectedScript = "XXXXXX",
|
||||
TesseractOCRDetectedScriptConf = "XXXXXX",
|
||||
TesseractOCRModuleVersion = "XXXXXX",
|
||||
TesseractOCRParameters = "XXXXXX",
|
||||
PDFModuleVersion = "XXXXXX",
|
||||
WordConfidenceInterval0To10 = "XXXXXX",
|
||||
WordConfidenceInterval11To20 = "XXXXXX",
|
||||
WordConfidenceInterval21To30 = "XXXXXX",
|
||||
WordConfidenceInterval31To40 = "XXXXXX",
|
||||
WordConfidenceInterval41To50 = "XXXXXX",
|
||||
WordConfidenceInterval51To60 = "XXXXXX",
|
||||
WordConfidenceInterval61To70 = "XXXXXX",
|
||||
WordConfidenceInterval71To80 = "XXXXXX",
|
||||
WordConfidenceInterval81To90 = "XXXXXX",
|
||||
WordConfidenceInterval91To100 = "XXXXXX",
|
||||
Album = "XXXXXX",
|
||||
Artist = "XXXXXX",
|
||||
Bitrate = "XXXXXX",
|
||||
Creator = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
Length = "XXXXXX",
|
||||
PreviewImage = "XXXXXX",
|
||||
Rotation = "XXXXXX",
|
||||
Title = "XXXXXX",
|
||||
Track = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
};
|
||||
|
||||
return new Models.ArchiveDotOrg.Files
|
||||
{
|
||||
File = [file]
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a File
|
||||
/// </summary>
|
||||
private static void Validate(Models.ArchiveDotOrg.File? file)
|
||||
{
|
||||
Assert.NotNull(file);
|
||||
Assert.Equal("XXXXXX", file.Name);
|
||||
Assert.Equal("XXXXXX", file.Source);
|
||||
Assert.Equal("XXXXXX", file.BitTorrentMagnetHash);
|
||||
Assert.Equal("XXXXXX", file.LastModifiedTime);
|
||||
Assert.Equal("XXXXXX", file.Size);
|
||||
Assert.Equal("XXXXXX", file.MD5);
|
||||
Assert.Equal("XXXXXX", file.CRC32);
|
||||
Assert.Equal("XXXXXX", file.SHA1);
|
||||
Assert.Equal("XXXXXX", file.FileCount);
|
||||
Assert.Equal("XXXXXX", file.Format);
|
||||
Assert.Equal("XXXXXX", file.Original);
|
||||
Assert.Equal("XXXXXX", file.Summation);
|
||||
Assert.Equal("XXXXXX", file.MatrixNumber);
|
||||
Assert.Equal("XXXXXX", file.CollectionCatalogNumber);
|
||||
Assert.Equal("XXXXXX", file.Publisher);
|
||||
Assert.Equal("XXXXXX", file.Comment);
|
||||
Assert.Equal("XXXXXX", file.ASRDetectedLang);
|
||||
Assert.Equal("XXXXXX", file.ASRDetectedLangConf);
|
||||
Assert.Equal("XXXXXX", file.ASRTranscribedLang);
|
||||
Assert.Equal("XXXXXX", file.WhisperASRModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.WhisperModelHash);
|
||||
Assert.Equal("XXXXXX", file.WhisperModelName);
|
||||
Assert.Equal("XXXXXX", file.WhisperVersion);
|
||||
Assert.Equal("XXXXXX", file.ClothCoverDetectionModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.hOCRCharToWordhOCRVersion);
|
||||
Assert.Equal("XXXXXX", file.hOCRCharToWordModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.hOCRFtsTexthOCRVersion);
|
||||
Assert.Equal("XXXXXX", file.hOCRFtsTextModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.hOCRPageIndexhOCRVersion);
|
||||
Assert.Equal("XXXXXX", file.hOCRPageIndexModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCR);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRConverted);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRDetectedLang);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRDetectedLangConf);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRDetectedScript);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRDetectedScriptConf);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.TesseractOCRParameters);
|
||||
Assert.Equal("XXXXXX", file.PDFModuleVersion);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval0To10);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval11To20);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval21To30);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval31To40);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval41To50);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval51To60);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval61To70);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval71To80);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval81To90);
|
||||
Assert.Equal("XXXXXX", file.WordConfidenceInterval91To100);
|
||||
Assert.Equal("XXXXXX", file.Album);
|
||||
Assert.Equal("XXXXXX", file.Artist);
|
||||
Assert.Equal("XXXXXX", file.Bitrate);
|
||||
Assert.Equal("XXXXXX", file.Creator);
|
||||
Assert.Equal("XXXXXX", file.Height);
|
||||
Assert.Equal("XXXXXX", file.Length);
|
||||
Assert.Equal("XXXXXX", file.PreviewImage);
|
||||
Assert.Equal("XXXXXX", file.Rotation);
|
||||
Assert.Equal("XXXXXX", file.Title);
|
||||
Assert.Equal("XXXXXX", file.Track);
|
||||
Assert.Equal("XXXXXX", file.Width);
|
||||
}
|
||||
}
|
||||
}
|
||||
111
SabreTools.Serialization.Test/CrossModel/AttractModeTests.cs
Normal file
111
SabreTools.Serialization.Test/CrossModel/AttractModeTests.cs
Normal file
@@ -0,0 +1,111 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class AttractModeTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.AttractMode();
|
||||
|
||||
// Build the data
|
||||
Models.AttractMode.MetadataFile mf = Build();
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.AttractMode.MetadataFile? newMf = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMf);
|
||||
Validate(newMf.Header);
|
||||
Assert.NotNull(newMf.Row);
|
||||
var newRow = Assert.Single(newMf.Row);
|
||||
Validate(newRow);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.AttractMode.MetadataFile Build()
|
||||
{
|
||||
string[] header = ["header"];
|
||||
|
||||
var row = new Models.AttractMode.Row
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Title = "XXXXXX",
|
||||
Emulator = "XXXXXX",
|
||||
CloneOf = "XXXXXX",
|
||||
Year = "XXXXXX",
|
||||
Manufacturer = "XXXXXX",
|
||||
Category = "XXXXXX",
|
||||
Players = "XXXXXX",
|
||||
Rotation = "XXXXXX",
|
||||
Control = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
DisplayCount = "XXXXXX",
|
||||
DisplayType = "XXXXXX",
|
||||
AltRomname = "XXXXXX",
|
||||
AltTitle = "XXXXXX",
|
||||
Extra = "XXXXXX",
|
||||
Buttons = "XXXXXX",
|
||||
Favorite = "XXXXXX",
|
||||
Tags = "XXXXXX",
|
||||
PlayedCount = "XXXXXX",
|
||||
PlayedTime = "XXXXXX",
|
||||
FileIsAvailable = "XXXXXX",
|
||||
};
|
||||
|
||||
return new Models.AttractMode.MetadataFile
|
||||
{
|
||||
Header = header,
|
||||
Row = [row],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a header
|
||||
/// </summary>
|
||||
private static void Validate(string[]? header)
|
||||
{
|
||||
Assert.NotNull(header);
|
||||
string column = Assert.Single(header);
|
||||
Assert.Equal("header", column);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Row
|
||||
/// </summary>
|
||||
private static void Validate(Models.AttractMode.Row? row)
|
||||
{
|
||||
Assert.NotNull(row);
|
||||
Assert.Equal("XXXXXX", row.Name);
|
||||
Assert.Equal("XXXXXX", row.Title);
|
||||
Assert.Equal("XXXXXX", row.Emulator);
|
||||
Assert.Equal("XXXXXX", row.CloneOf);
|
||||
Assert.Equal("XXXXXX", row.Year);
|
||||
Assert.Equal("XXXXXX", row.Manufacturer);
|
||||
Assert.Equal("XXXXXX", row.Category);
|
||||
Assert.Equal("XXXXXX", row.Players);
|
||||
Assert.Equal("XXXXXX", row.Rotation);
|
||||
Assert.Equal("XXXXXX", row.Control);
|
||||
Assert.Equal("XXXXXX", row.Status);
|
||||
Assert.Equal("XXXXXX", row.DisplayCount);
|
||||
Assert.Equal("XXXXXX", row.DisplayType);
|
||||
Assert.Equal("XXXXXX", row.AltRomname);
|
||||
Assert.Equal("XXXXXX", row.AltTitle);
|
||||
Assert.Equal("XXXXXX", row.Extra);
|
||||
Assert.Equal("XXXXXX", row.Buttons);
|
||||
Assert.Equal("XXXXXX", row.Favorite);
|
||||
Assert.Equal("XXXXXX", row.Tags);
|
||||
Assert.Equal("XXXXXX", row.PlayedCount);
|
||||
Assert.Equal("XXXXXX", row.PlayedTime);
|
||||
Assert.Equal("XXXXXX", row.FileIsAvailable);
|
||||
}
|
||||
}
|
||||
}
|
||||
492
SabreTools.Serialization.Test/CrossModel/ClrMameProTests.cs
Normal file
492
SabreTools.Serialization.Test/CrossModel/ClrMameProTests.cs
Normal file
@@ -0,0 +1,492 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class ClrMameProTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripGameTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.ClrMamePro();
|
||||
|
||||
// Build the data
|
||||
Models.ClrMamePro.MetadataFile mf = Build(game: true);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.ClrMamePro.MetadataFile? newMf = serializer.Deserialize(metadata, game: true);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMf);
|
||||
Validate(newMf.ClrMamePro);
|
||||
Assert.NotNull(newMf.Game);
|
||||
var newGame = Assert.Single(newMf.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMachineTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.ClrMamePro();
|
||||
|
||||
// Build the data
|
||||
Models.ClrMamePro.MetadataFile mf = Build(game: false);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.ClrMamePro.MetadataFile? newMf = serializer.Deserialize(metadata, game: false);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMf);
|
||||
Validate(newMf.ClrMamePro);
|
||||
Assert.NotNull(newMf.Game);
|
||||
var newGame = Assert.Single(newMf.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.ClrMamePro.MetadataFile Build(bool game)
|
||||
{
|
||||
var cmp = new Models.ClrMamePro.ClrMamePro
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
RootDir = "XXXXXX",
|
||||
Category = "XXXXXX",
|
||||
Version = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
Author = "XXXXXX",
|
||||
Homepage = "XXXXXX",
|
||||
Url = "XXXXXX",
|
||||
Comment = "XXXXXX",
|
||||
Header = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
ForceMerging = "XXXXXX",
|
||||
ForceZipping = "XXXXXX",
|
||||
ForcePacking = "XXXXXX",
|
||||
};
|
||||
|
||||
var release = new Models.ClrMamePro.Release
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Language = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var biosset = new Models.ClrMamePro.BiosSet
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var rom = new Models.ClrMamePro.Rom
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Flags = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
SHA256 = "XXXXXX",
|
||||
SHA384 = "XXXXXX",
|
||||
SHA512 = "XXXXXX",
|
||||
SpamSum = "XXXXXX",
|
||||
xxHash364 = "XXXXXX",
|
||||
xxHash3128 = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Offs = "XXXXXX",
|
||||
Serial = "XXXXXX",
|
||||
Header = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
MIA = "XXXXXX",
|
||||
};
|
||||
|
||||
var disk = new Models.ClrMamePro.Disk
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Flags = "XXXXXX",
|
||||
};
|
||||
|
||||
var sample = new Models.ClrMamePro.Sample
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var archive = new Models.ClrMamePro.Archive
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var media = new Models.ClrMamePro.Media
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
SHA256 = "XXXXXX",
|
||||
SpamSum = "XXXXXX",
|
||||
};
|
||||
|
||||
var chip = new Models.ClrMamePro.Chip
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
Flags = "XXXXXX",
|
||||
Clock = "XXXXXX",
|
||||
};
|
||||
|
||||
var video = new Models.ClrMamePro.Video
|
||||
{
|
||||
Screen = "XXXXXX",
|
||||
Orientation = "XXXXXX",
|
||||
X = "XXXXXX",
|
||||
Y = "XXXXXX",
|
||||
AspectX = "XXXXXX",
|
||||
AspectY = "XXXXXX",
|
||||
Freq = "XXXXXX",
|
||||
};
|
||||
|
||||
var sound = new Models.ClrMamePro.Sound
|
||||
{
|
||||
Channels = "XXXXXX",
|
||||
};
|
||||
|
||||
var input = new Models.ClrMamePro.Input
|
||||
{
|
||||
Players = "XXXXXX",
|
||||
Control = "XXXXXX",
|
||||
Buttons = "XXXXXX",
|
||||
Coins = "XXXXXX",
|
||||
Tilt = "XXXXXX",
|
||||
Service = "XXXXXX",
|
||||
};
|
||||
|
||||
var dipswitch = new Models.ClrMamePro.DipSwitch
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Entry = ["XXXXXX"],
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var driver = new Models.ClrMamePro.Driver
|
||||
{
|
||||
Status = "XXXXXX",
|
||||
Color = "XXXXXX",
|
||||
Sound = "XXXXXX",
|
||||
PaletteSize = "XXXXXX",
|
||||
Blit = "XXXXXX",
|
||||
};
|
||||
|
||||
// TODO: This omits Set, should that have a separate case?
|
||||
Models.ClrMamePro.GameBase gameBase = game
|
||||
? new Models.ClrMamePro.Game()
|
||||
: new Models.ClrMamePro.Machine();
|
||||
gameBase.Name = "XXXXXX";
|
||||
gameBase.Description = "XXXXXX";
|
||||
gameBase.Year = "XXXXXX";
|
||||
gameBase.Manufacturer = "XXXXXX";
|
||||
gameBase.Category = "XXXXXX";
|
||||
gameBase.CloneOf = "XXXXXX";
|
||||
gameBase.RomOf = "XXXXXX";
|
||||
gameBase.SampleOf = "XXXXXX";
|
||||
gameBase.Release = [release];
|
||||
gameBase.BiosSet = [biosset];
|
||||
gameBase.Rom = [rom];
|
||||
gameBase.Disk = [disk];
|
||||
gameBase.Sample = [sample];
|
||||
gameBase.Archive = [archive];
|
||||
gameBase.Media = [media];
|
||||
gameBase.Chip = [chip];
|
||||
gameBase.Video = [video];
|
||||
gameBase.Sound = sound;
|
||||
gameBase.Input = input;
|
||||
gameBase.DipSwitch = [dipswitch];
|
||||
gameBase.Driver = driver;
|
||||
|
||||
return new Models.ClrMamePro.MetadataFile
|
||||
{
|
||||
ClrMamePro = cmp,
|
||||
Game = [gameBase],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ClrMamePro
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.ClrMamePro? cmp)
|
||||
{
|
||||
Assert.NotNull(cmp);
|
||||
Assert.Equal("XXXXXX", cmp.Name);
|
||||
Assert.Equal("XXXXXX", cmp.Description);
|
||||
Assert.Equal("XXXXXX", cmp.RootDir);
|
||||
Assert.Equal("XXXXXX", cmp.Category);
|
||||
Assert.Equal("XXXXXX", cmp.Version);
|
||||
Assert.Equal("XXXXXX", cmp.Date);
|
||||
Assert.Equal("XXXXXX", cmp.Author);
|
||||
Assert.Equal("XXXXXX", cmp.Homepage);
|
||||
Assert.Equal("XXXXXX", cmp.Url);
|
||||
Assert.Equal("XXXXXX", cmp.Comment);
|
||||
Assert.Equal("XXXXXX", cmp.Header);
|
||||
Assert.Equal("XXXXXX", cmp.Type);
|
||||
Assert.Equal("XXXXXX", cmp.ForceMerging);
|
||||
Assert.Equal("XXXXXX", cmp.ForceZipping);
|
||||
Assert.Equal("XXXXXX", cmp.ForcePacking);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a GameBase
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.GameBase? gb)
|
||||
{
|
||||
Assert.NotNull(gb);
|
||||
Assert.Equal("XXXXXX", gb.Name);
|
||||
Assert.Equal("XXXXXX", gb.Description);
|
||||
Assert.Equal("XXXXXX", gb.Year);
|
||||
Assert.Equal("XXXXXX", gb.Manufacturer);
|
||||
Assert.Equal("XXXXXX", gb.Category);
|
||||
Assert.Equal("XXXXXX", gb.CloneOf);
|
||||
Assert.Equal("XXXXXX", gb.RomOf);
|
||||
Assert.Equal("XXXXXX", gb.SampleOf);
|
||||
|
||||
Assert.NotNull(gb.Release);
|
||||
var release = Assert.Single(gb.Release);
|
||||
Validate(release);
|
||||
|
||||
Assert.NotNull(gb.BiosSet);
|
||||
var biosset = Assert.Single(gb.BiosSet);
|
||||
Validate(biosset);
|
||||
|
||||
Assert.NotNull(gb.Rom);
|
||||
var rom = Assert.Single(gb.Rom);
|
||||
Validate(rom);
|
||||
|
||||
Assert.NotNull(gb.Disk);
|
||||
var disk = Assert.Single(gb.Disk);
|
||||
Validate(disk);
|
||||
|
||||
Assert.NotNull(gb.Sample);
|
||||
var sample = Assert.Single(gb.Sample);
|
||||
Validate(sample);
|
||||
|
||||
Assert.NotNull(gb.Archive);
|
||||
var archive = Assert.Single(gb.Archive);
|
||||
Validate(archive);
|
||||
|
||||
Assert.NotNull(gb.Media);
|
||||
var media = Assert.Single(gb.Media);
|
||||
Validate(media);
|
||||
|
||||
Assert.NotNull(gb.Chip);
|
||||
var chip = Assert.Single(gb.Chip);
|
||||
Validate(chip);
|
||||
|
||||
Assert.NotNull(gb.Video);
|
||||
var video = Assert.Single(gb.Video);
|
||||
Validate(video);
|
||||
|
||||
Validate(gb.Sound);
|
||||
Validate(gb.Input);
|
||||
|
||||
Assert.NotNull(gb.DipSwitch);
|
||||
var dipswitch = Assert.Single(gb.DipSwitch);
|
||||
Validate(dipswitch);
|
||||
|
||||
Validate(gb.Driver);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Release
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Release? release)
|
||||
{
|
||||
Assert.NotNull(release);
|
||||
Assert.Equal("XXXXXX", release.Name);
|
||||
Assert.Equal("XXXXXX", release.Region);
|
||||
Assert.Equal("XXXXXX", release.Language);
|
||||
Assert.Equal("XXXXXX", release.Date);
|
||||
Assert.Equal("XXXXXX", release.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a BiosSet
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.BiosSet? biosset)
|
||||
{
|
||||
Assert.NotNull(biosset);
|
||||
Assert.Equal("XXXXXX", biosset.Name);
|
||||
Assert.Equal("XXXXXX", biosset.Description);
|
||||
Assert.Equal("XXXXXX", biosset.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Rom
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Rom? rom)
|
||||
{
|
||||
Assert.NotNull(rom);
|
||||
Assert.Equal("XXXXXX", rom.Name);
|
||||
Assert.Equal("XXXXXX", rom.Size);
|
||||
Assert.Equal("XXXXXX", rom.CRC);
|
||||
Assert.Equal("XXXXXX", rom.MD5);
|
||||
Assert.Equal("XXXXXX", rom.SHA1);
|
||||
Assert.Equal("XXXXXX", rom.Merge);
|
||||
Assert.Equal("XXXXXX", rom.Status);
|
||||
Assert.Equal("XXXXXX", rom.Flags);
|
||||
Assert.Equal("XXXXXX", rom.Date);
|
||||
Assert.Equal("XXXXXX", rom.SHA256);
|
||||
Assert.Equal("XXXXXX", rom.SHA384);
|
||||
Assert.Equal("XXXXXX", rom.SHA512);
|
||||
Assert.Equal("XXXXXX", rom.SpamSum);
|
||||
Assert.Equal("XXXXXX", rom.xxHash364);
|
||||
Assert.Equal("XXXXXX", rom.xxHash3128);
|
||||
Assert.Equal("XXXXXX", rom.Region);
|
||||
Assert.Equal("XXXXXX", rom.Offs);
|
||||
Assert.Equal("XXXXXX", rom.Serial);
|
||||
Assert.Equal("XXXXXX", rom.Header);
|
||||
Assert.Equal("XXXXXX", rom.Inverted);
|
||||
Assert.Equal("XXXXXX", rom.MIA);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Disk
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Disk? disk)
|
||||
{
|
||||
Assert.NotNull(disk);
|
||||
Assert.Equal("XXXXXX", disk.Name);
|
||||
Assert.Equal("XXXXXX", disk.MD5);
|
||||
Assert.Equal("XXXXXX", disk.SHA1);
|
||||
Assert.Equal("XXXXXX", disk.Merge);
|
||||
Assert.Equal("XXXXXX", disk.Status);
|
||||
Assert.Equal("XXXXXX", disk.Flags);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sample
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Sample? sample)
|
||||
{
|
||||
Assert.NotNull(sample);
|
||||
Assert.Equal("XXXXXX", sample.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Archive
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Archive? archive)
|
||||
{
|
||||
Assert.NotNull(archive);
|
||||
Assert.Equal("XXXXXX", archive.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Media
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Media? media)
|
||||
{
|
||||
Assert.NotNull(media);
|
||||
Assert.Equal("XXXXXX", media.Name);
|
||||
Assert.Equal("XXXXXX", media.MD5);
|
||||
Assert.Equal("XXXXXX", media.SHA1);
|
||||
Assert.Equal("XXXXXX", media.SHA256);
|
||||
Assert.Equal("XXXXXX", media.SpamSum);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Chip
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Chip? chip)
|
||||
{
|
||||
Assert.NotNull(chip);
|
||||
Assert.Equal("XXXXXX", chip.Type);
|
||||
Assert.Equal("XXXXXX", chip.Name);
|
||||
Assert.Equal("XXXXXX", chip.Flags);
|
||||
Assert.Equal("XXXXXX", chip.Clock);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Video
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Video? video)
|
||||
{
|
||||
Assert.NotNull(video);
|
||||
Assert.Equal("XXXXXX", video.Screen);
|
||||
Assert.Equal("XXXXXX", video.Orientation);
|
||||
Assert.Equal("XXXXXX", video.X);
|
||||
Assert.Equal("XXXXXX", video.Y);
|
||||
Assert.Equal("XXXXXX", video.AspectX);
|
||||
Assert.Equal("XXXXXX", video.AspectY);
|
||||
Assert.Equal("XXXXXX", video.Freq);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sound
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Sound? sound)
|
||||
{
|
||||
Assert.NotNull(sound);
|
||||
Assert.Equal("XXXXXX", sound.Channels);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Input
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Input? input)
|
||||
{
|
||||
Assert.NotNull(input);
|
||||
Assert.Equal("XXXXXX", input.Players);
|
||||
Assert.Equal("XXXXXX", input.Control);
|
||||
Assert.Equal("XXXXXX", input.Buttons);
|
||||
Assert.Equal("XXXXXX", input.Coins);
|
||||
Assert.Equal("XXXXXX", input.Tilt);
|
||||
Assert.Equal("XXXXXX", input.Service);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipSwitch
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.DipSwitch? dipswitch)
|
||||
{
|
||||
Assert.NotNull(dipswitch);
|
||||
Assert.Equal("XXXXXX", dipswitch.Name);
|
||||
|
||||
Assert.NotNull(dipswitch.Entry);
|
||||
string entry = Assert.Single(dipswitch.Entry);
|
||||
Assert.Equal("XXXXXX", entry);
|
||||
|
||||
Assert.Equal("XXXXXX", dipswitch.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Driver
|
||||
/// </summary>
|
||||
private static void Validate(Models.ClrMamePro.Driver? driver)
|
||||
{
|
||||
Assert.NotNull(driver);
|
||||
Assert.Equal("XXXXXX", driver.Status);
|
||||
Assert.Equal("XXXXXX", driver.Color);
|
||||
Assert.Equal("XXXXXX", driver.Sound);
|
||||
Assert.Equal("XXXXXX", driver.PaletteSize);
|
||||
Assert.Equal("XXXXXX", driver.Blit);
|
||||
}
|
||||
}
|
||||
}
|
||||
110
SabreTools.Serialization.Test/CrossModel/DosCenterTests.cs
Normal file
110
SabreTools.Serialization.Test/CrossModel/DosCenterTests.cs
Normal file
@@ -0,0 +1,110 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class DosCenterTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.DosCenter();
|
||||
|
||||
// Build the data
|
||||
Models.DosCenter.MetadataFile mf = Build();
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.DosCenter.MetadataFile? newMf = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMf);
|
||||
Validate(newMf.DosCenter);
|
||||
Assert.NotNull(newMf.Game);
|
||||
var newGame = Assert.Single(newMf.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.DosCenter.MetadataFile Build()
|
||||
{
|
||||
var dc = new Models.DosCenter.DosCenter
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
Version = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
Author = "XXXXXX",
|
||||
Homepage = "XXXXXX",
|
||||
Comment = "XXXXXX",
|
||||
};
|
||||
|
||||
var file = new Models.DosCenter.File
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
};
|
||||
|
||||
var game = new Models.DosCenter.Game
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
File = [file],
|
||||
};
|
||||
|
||||
return new Models.DosCenter.MetadataFile
|
||||
{
|
||||
DosCenter = dc,
|
||||
Game = [game],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DosCenter
|
||||
/// </summary>
|
||||
private static void Validate(Models.DosCenter.DosCenter? cmp)
|
||||
{
|
||||
Assert.NotNull(cmp);
|
||||
Assert.Equal("XXXXXX", cmp.Name);
|
||||
Assert.Equal("XXXXXX", cmp.Description);
|
||||
Assert.Equal("XXXXXX", cmp.Version);
|
||||
Assert.Equal("XXXXXX", cmp.Date);
|
||||
Assert.Equal("XXXXXX", cmp.Author);
|
||||
Assert.Equal("XXXXXX", cmp.Homepage);
|
||||
Assert.Equal("XXXXXX", cmp.Comment);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Game
|
||||
/// </summary>
|
||||
private static void Validate(Models.DosCenter.Game? game)
|
||||
{
|
||||
Assert.NotNull(game);
|
||||
Assert.Equal("XXXXXX", game.Name);
|
||||
|
||||
Assert.NotNull(game.File);
|
||||
var file = Assert.Single(game.File);
|
||||
Validate(file);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a File
|
||||
/// </summary>
|
||||
private static void Validate(Models.DosCenter.File? rom)
|
||||
{
|
||||
Assert.NotNull(rom);
|
||||
Assert.Equal("XXXXXX", rom.Name);
|
||||
Assert.Equal("XXXXXX", rom.Size);
|
||||
Assert.Equal("XXXXXX", rom.CRC);
|
||||
Assert.Equal("XXXXXX", rom.SHA1);
|
||||
Assert.Equal("XXXXXX", rom.Date);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class EverdriveSMDBTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.EverdriveSMDB();
|
||||
|
||||
// Build the data
|
||||
Models.EverdriveSMDB.MetadataFile mf = Build();
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.EverdriveSMDB.MetadataFile? newMf = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMf);
|
||||
Assert.NotNull(newMf.Row);
|
||||
var newRow = Assert.Single(newMf.Row);
|
||||
Validate(newRow);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.EverdriveSMDB.MetadataFile Build()
|
||||
{
|
||||
var row = new Models.EverdriveSMDB.Row
|
||||
{
|
||||
SHA256 = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
CRC32 = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
};
|
||||
|
||||
return new Models.EverdriveSMDB.MetadataFile
|
||||
{
|
||||
Row = [row],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Row
|
||||
/// </summary>
|
||||
private static void Validate(Models.EverdriveSMDB.Row? row)
|
||||
{
|
||||
Assert.NotNull(row);
|
||||
Assert.Equal("XXXXXX", row.SHA256);
|
||||
Assert.Equal("XXXXXX", row.Name);
|
||||
Assert.Equal("XXXXXX", row.SHA1);
|
||||
Assert.Equal("XXXXXX", row.MD5);
|
||||
Assert.Equal("XXXXXX", row.CRC32);
|
||||
Assert.Equal("XXXXXX", row.Size);
|
||||
}
|
||||
}
|
||||
}
|
||||
326
SabreTools.Serialization.Test/CrossModel/HashfileTests.cs
Normal file
326
SabreTools.Serialization.Test/CrossModel/HashfileTests.cs
Normal file
@@ -0,0 +1,326 @@
|
||||
using System;
|
||||
using SabreTools.Hashing;
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class HashfileTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripSFVTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.CRC32);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.CRC32);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.SFV);
|
||||
var newSfv = Assert.Single(newHf.SFV);
|
||||
Validate(newSfv);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMD2Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.MD2);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.MD2);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.MD2);
|
||||
var newMd2 = Assert.Single(newHf.MD2);
|
||||
Validate(newMd2);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMD4Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.MD4);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.MD4);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.MD4);
|
||||
var newMd4 = Assert.Single(newHf.MD4);
|
||||
Validate(newMd4);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMD5Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.MD5);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.MD5);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.MD5);
|
||||
var newMd5 = Assert.Single(newHf.MD5);
|
||||
Validate(newMd5);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripSHA1Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.SHA1);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.SHA1);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.SHA1);
|
||||
var newSha1 = Assert.Single(newHf.SHA1);
|
||||
Validate(newSha1);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripSHA256Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.SHA256);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.SHA256);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.SHA256);
|
||||
var newSha256 = Assert.Single(newHf.SHA256);
|
||||
Validate(newSha256);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripSHA384Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.SHA384);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.SHA384);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.SHA384);
|
||||
var newSha384 = Assert.Single(newHf.SHA384);
|
||||
Validate(newSha384);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripSHA512Test()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.SHA512);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.SHA512);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.SHA512);
|
||||
var newSha512 = Assert.Single(newHf.SHA512);
|
||||
Validate(newSha512);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripSpamSumTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Hashfile();
|
||||
|
||||
// Build the data
|
||||
Models.Hashfile.Hashfile hf = Build(HashType.SpamSum);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(hf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Hashfile.Hashfile? newHf = serializer.Deserialize(metadata, HashType.SpamSum);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newHf);
|
||||
Assert.NotNull(newHf.SpamSum);
|
||||
var newSpamsum = Assert.Single(newHf.SpamSum);
|
||||
Validate(newSpamsum);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.Hashfile.Hashfile Build(HashType hashType)
|
||||
{
|
||||
return hashType switch
|
||||
{
|
||||
HashType.CRC32 => new Models.Hashfile.Hashfile { SFV = [new Models.Hashfile.SFV { File = "XXXXXX", Hash = "XXXXXX" }] },
|
||||
HashType.MD2 => new Models.Hashfile.Hashfile { MD2 = [new Models.Hashfile.MD2 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.MD4 => new Models.Hashfile.Hashfile { MD4 = [new Models.Hashfile.MD4 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.MD5 => new Models.Hashfile.Hashfile { MD5 = [new Models.Hashfile.MD5 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.SHA1 => new Models.Hashfile.Hashfile { SHA1 = [new Models.Hashfile.SHA1 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.SHA256 => new Models.Hashfile.Hashfile { SHA256 = [new Models.Hashfile.SHA256 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.SHA384 => new Models.Hashfile.Hashfile { SHA384 = [new Models.Hashfile.SHA384 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.SHA512 => new Models.Hashfile.Hashfile { SHA512 = [new Models.Hashfile.SHA512 { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
HashType.SpamSum => new Models.Hashfile.Hashfile { SpamSum = [new Models.Hashfile.SpamSum { Hash = "XXXXXX", File = "XXXXXX" }] },
|
||||
_ => throw new ArgumentOutOfRangeException(),
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SFV
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.SFV? sfv)
|
||||
{
|
||||
Assert.NotNull(sfv);
|
||||
Assert.Equal("XXXXXX", sfv.File);
|
||||
Assert.Equal("XXXXXX", sfv.Hash);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a MD2
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.MD2? md2)
|
||||
{
|
||||
Assert.NotNull(md2);
|
||||
Assert.Equal("XXXXXX", md2.Hash);
|
||||
Assert.Equal("XXXXXX", md2.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a MD4
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.MD4? md4)
|
||||
{
|
||||
Assert.NotNull(md4);
|
||||
Assert.Equal("XXXXXX", md4.Hash);
|
||||
Assert.Equal("XXXXXX", md4.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a MD5
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.MD5? md5)
|
||||
{
|
||||
Assert.NotNull(md5);
|
||||
Assert.Equal("XXXXXX", md5.Hash);
|
||||
Assert.Equal("XXXXXX", md5.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SHA1
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.SHA1? sha1)
|
||||
{
|
||||
Assert.NotNull(sha1);
|
||||
Assert.Equal("XXXXXX", sha1.Hash);
|
||||
Assert.Equal("XXXXXX", sha1.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SHA256
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.SHA256? sha256)
|
||||
{
|
||||
Assert.NotNull(sha256);
|
||||
Assert.Equal("XXXXXX", sha256.Hash);
|
||||
Assert.Equal("XXXXXX", sha256.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SHA384
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.SHA384? sha384)
|
||||
{
|
||||
Assert.NotNull(sha384);
|
||||
Assert.Equal("XXXXXX", sha384.Hash);
|
||||
Assert.Equal("XXXXXX", sha384.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SHA512
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.SHA512? sha512)
|
||||
{
|
||||
Assert.NotNull(sha512);
|
||||
Assert.Equal("XXXXXX", sha512.Hash);
|
||||
Assert.Equal("XXXXXX", sha512.File);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SpamSum
|
||||
/// </summary>
|
||||
private static void Validate(Models.Hashfile.SpamSum? spamsum)
|
||||
{
|
||||
Assert.NotNull(spamsum);
|
||||
Assert.Equal("XXXXXX", spamsum.Hash);
|
||||
Assert.Equal("XXXXXX", spamsum.File);
|
||||
}
|
||||
}
|
||||
}
|
||||
127
SabreTools.Serialization.Test/CrossModel/ListromTests.cs
Normal file
127
SabreTools.Serialization.Test/CrossModel/ListromTests.cs
Normal file
@@ -0,0 +1,127 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class ListromTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Listrom();
|
||||
|
||||
// Build the data
|
||||
Models.Listrom.MetadataFile mf = Build();
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mf);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listrom.MetadataFile? newMf = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMf);
|
||||
Assert.NotNull(newMf.Set);
|
||||
Assert.Equal(2, newMf.Set.Length);
|
||||
|
||||
ValidateDevice(newMf.Set[0]);
|
||||
ValidateDriver(newMf.Set[1]);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.Listrom.MetadataFile Build()
|
||||
{
|
||||
var rom = new Models.Listrom.Row
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
Bad = true,
|
||||
CRC = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
NoGoodDumpKnown = false,
|
||||
};
|
||||
|
||||
var disk = new Models.Listrom.Row
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Bad = false,
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
NoGoodDumpKnown = true,
|
||||
};
|
||||
|
||||
var device = new Models.Listrom.Set()
|
||||
{
|
||||
Device = "XXXXXX",
|
||||
Row = [rom],
|
||||
};
|
||||
|
||||
var driver = new Models.Listrom.Set()
|
||||
{
|
||||
Driver = "XXXXXX",
|
||||
Row = [disk],
|
||||
};
|
||||
|
||||
return new Models.Listrom.MetadataFile
|
||||
{
|
||||
Set = [device, driver],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Set
|
||||
/// </summary>
|
||||
private static void ValidateDevice(Models.Listrom.Set? set)
|
||||
{
|
||||
Assert.NotNull(set);
|
||||
Assert.Equal("XXXXXX", set.Device);
|
||||
|
||||
Assert.NotNull(set.Row);
|
||||
var row = Assert.Single(set.Row);
|
||||
ValidateRom(row);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Set
|
||||
/// </summary>
|
||||
private static void ValidateDriver(Models.Listrom.Set? set)
|
||||
{
|
||||
Assert.NotNull(set);
|
||||
Assert.Equal("XXXXXX", set.Driver);
|
||||
|
||||
Assert.NotNull(set.Row);
|
||||
var row = Assert.Single(set.Row);
|
||||
ValidateDisk(row);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Row
|
||||
/// </summary>
|
||||
private static void ValidateRom(Models.Listrom.Row? row)
|
||||
{
|
||||
Assert.NotNull(row);
|
||||
Assert.Equal("XXXXXX", row.Name);
|
||||
Assert.Equal("XXXXXX", row.Size);
|
||||
Assert.True(row.Bad);
|
||||
Assert.Equal("XXXXXX", row.CRC);
|
||||
Assert.Equal("XXXXXX", row.SHA1);
|
||||
Assert.False(row.NoGoodDumpKnown);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Row
|
||||
/// </summary>
|
||||
private static void ValidateDisk(Models.Listrom.Row? row)
|
||||
{
|
||||
Assert.NotNull(row);
|
||||
Assert.Equal("XXXXXX", row.Name);
|
||||
Assert.False(row.Bad);
|
||||
Assert.Equal("XXXXXX", row.MD5);
|
||||
Assert.Equal("XXXXXX", row.SHA1);
|
||||
Assert.True(row.NoGoodDumpKnown);
|
||||
}
|
||||
}
|
||||
}
|
||||
878
SabreTools.Serialization.Test/CrossModel/ListxmlTests.cs
Normal file
878
SabreTools.Serialization.Test/CrossModel/ListxmlTests.cs
Normal file
@@ -0,0 +1,878 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class ListxmlTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripGameTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Listxml();
|
||||
|
||||
// Build the data
|
||||
Models.Listxml.Mame mame = Build(game: true);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mame);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listxml.Mame? newMame = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMame);
|
||||
Assert.Equal("XXXXXX", newMame.Build);
|
||||
Assert.Equal("XXXXXX", newMame.Debug);
|
||||
Assert.Equal("XXXXXX", newMame.MameConfig);
|
||||
|
||||
Assert.NotNull(newMame.Game);
|
||||
var newGame = Assert.Single(newMame.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMachineTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Listxml();
|
||||
|
||||
// Build the data
|
||||
Models.Listxml.Mame mame = Build(game: false);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(mame);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listxml.Mame? newMame = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMame);
|
||||
Assert.Equal("XXXXXX", newMame.Build);
|
||||
Assert.Equal("XXXXXX", newMame.Debug);
|
||||
Assert.Equal("XXXXXX", newMame.MameConfig);
|
||||
|
||||
Assert.NotNull(newMame.Game);
|
||||
var newGame = Assert.Single(newMame.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.Listxml.Mame Build(bool game)
|
||||
{
|
||||
var biosset = new Models.Listxml.BiosSet
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var rom = new Models.Listxml.Rom
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Bios = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Offset = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Optional = "XXXXXX",
|
||||
Dispose = "XXXXXX",
|
||||
SoundOnly = "XXXXXX",
|
||||
};
|
||||
|
||||
var disk = new Models.Listxml.Disk
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Index = "XXXXXX",
|
||||
Writable = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Optional = "XXXXXX",
|
||||
};
|
||||
|
||||
var deviceref = new Models.Listxml.DeviceRef
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var sample = new Models.Listxml.Sample
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var chip = new Models.Listxml.Chip
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
SoundOnly = "XXXXXX",
|
||||
Clock = "XXXXXX",
|
||||
};
|
||||
|
||||
var display = new Models.Listxml.Display
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
Rotate = "XXXXXX",
|
||||
FlipX = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
Refresh = "XXXXXX",
|
||||
PixClock = "XXXXXX",
|
||||
HTotal = "XXXXXX",
|
||||
HBEnd = "XXXXXX",
|
||||
HBStart = "XXXXXX",
|
||||
VTotal = "XXXXXX",
|
||||
VBEnd = "XXXXXX",
|
||||
VBStart = "XXXXXX",
|
||||
};
|
||||
|
||||
var video = new Models.Listxml.Video
|
||||
{
|
||||
Screen = "XXXXXX",
|
||||
Orientation = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
AspectX = "XXXXXX",
|
||||
AspectY = "XXXXXX",
|
||||
Refresh = "XXXXXX",
|
||||
};
|
||||
|
||||
var sound = new Models.Listxml.Sound
|
||||
{
|
||||
Channels = "XXXXXX",
|
||||
};
|
||||
|
||||
var control = new Models.Listxml.Control
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Player = "XXXXXX",
|
||||
Buttons = "XXXXXX",
|
||||
ReqButtons = "XXXXXX",
|
||||
Minimum = "XXXXXX",
|
||||
Maximum = "XXXXXX",
|
||||
Sensitivity = "XXXXXX",
|
||||
KeyDelta = "XXXXXX",
|
||||
Reverse = "XXXXXX",
|
||||
Ways = "XXXXXX",
|
||||
Ways2 = "XXXXXX",
|
||||
Ways3 = "XXXXXX",
|
||||
};
|
||||
|
||||
var input = new Models.Listxml.Input
|
||||
{
|
||||
Service = "XXXXXX",
|
||||
Tilt = "XXXXXX",
|
||||
Players = "XXXXXX",
|
||||
//ControlAttr = "XXXXXX", // Mututally exclusive with input.Control
|
||||
Buttons = "XXXXXX",
|
||||
Coins = "XXXXXX",
|
||||
Control = [control],
|
||||
};
|
||||
|
||||
var condition = new Models.Listxml.Condition
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Relation = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
};
|
||||
|
||||
var diplocation = new Models.Listxml.DipLocation
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Number = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
};
|
||||
|
||||
var dipvalue = new Models.Listxml.DipValue
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var dipswitch = new Models.Listxml.DipSwitch
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Condition = condition,
|
||||
DipLocation = [diplocation],
|
||||
DipValue = [dipvalue],
|
||||
};
|
||||
|
||||
var conflocation = new Models.Listxml.ConfLocation
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Number = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
};
|
||||
|
||||
var confsetting = new Models.Listxml.ConfSetting
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var configuration = new Models.Listxml.Configuration
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Condition = condition,
|
||||
ConfLocation = [conflocation],
|
||||
ConfSetting = [confsetting],
|
||||
};
|
||||
|
||||
var analog = new Models.Listxml.Analog
|
||||
{
|
||||
Mask = "XXXXXX",
|
||||
};
|
||||
|
||||
var port = new Models.Listxml.Port
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Analog = [analog],
|
||||
};
|
||||
|
||||
var adjuster = new Models.Listxml.Adjuster
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var driver = new Models.Listxml.Driver
|
||||
{
|
||||
Status = "XXXXXX",
|
||||
Color = "XXXXXX",
|
||||
Sound = "XXXXXX",
|
||||
PaletteSize = "XXXXXX",
|
||||
Emulation = "XXXXXX",
|
||||
Cocktail = "XXXXXX",
|
||||
SaveState = "XXXXXX",
|
||||
RequiresArtwork = "XXXXXX",
|
||||
Unofficial = "XXXXXX",
|
||||
NoSoundHardware = "XXXXXX",
|
||||
Incomplete = "XXXXXX",
|
||||
};
|
||||
|
||||
var feature = new Models.Listxml.Feature
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Overall = "XXXXXX",
|
||||
};
|
||||
|
||||
var instance = new Models.Listxml.Instance
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
BriefName = "XXXXXX",
|
||||
};
|
||||
|
||||
var extension = new Models.Listxml.Extension
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var device = new Models.Listxml.Device
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
FixedImage = "XXXXXX",
|
||||
Mandatory = "XXXXXX",
|
||||
Interface = "XXXXXX",
|
||||
Instance = instance,
|
||||
Extension = [extension],
|
||||
};
|
||||
|
||||
var slotOption = new Models.Listxml.SlotOption
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
DevName = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var slot = new Models.Listxml.Slot
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
SlotOption = [slotOption],
|
||||
};
|
||||
|
||||
var softwarelist = new Models.Listxml.SoftwareList
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Filter = "XXXXXX",
|
||||
};
|
||||
|
||||
var ramoption = new Models.Listxml.RamOption
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Content = "XXXXXX",
|
||||
};
|
||||
|
||||
Models.Listxml.GameBase gameBase = game
|
||||
? new Models.Listxml.Game()
|
||||
: new Models.Listxml.Machine();
|
||||
gameBase.Name = "XXXXXX";
|
||||
gameBase.SourceFile = "XXXXXX";
|
||||
gameBase.IsBios = "XXXXXX";
|
||||
gameBase.IsDevice = "XXXXXX";
|
||||
gameBase.IsMechanical = "XXXXXX";
|
||||
gameBase.Runnable = "XXXXXX";
|
||||
gameBase.CloneOf = "XXXXXX";
|
||||
gameBase.RomOf = "XXXXXX";
|
||||
gameBase.SampleOf = "XXXXXX";
|
||||
gameBase.Description = "XXXXXX";
|
||||
gameBase.Year = "XXXXXX";
|
||||
gameBase.Manufacturer = "XXXXXX";
|
||||
gameBase.History = "XXXXXX";
|
||||
gameBase.BiosSet = [biosset];
|
||||
gameBase.Rom = [rom];
|
||||
gameBase.Disk = [disk];
|
||||
gameBase.DeviceRef = [deviceref];
|
||||
gameBase.Sample = [sample];
|
||||
gameBase.Chip = [chip];
|
||||
gameBase.Display = [display];
|
||||
gameBase.Video = [video];
|
||||
gameBase.Sound = sound;
|
||||
gameBase.Input = input;
|
||||
gameBase.DipSwitch = [dipswitch];
|
||||
gameBase.Configuration = [configuration];
|
||||
gameBase.Port = [port];
|
||||
gameBase.Adjuster = [adjuster];
|
||||
gameBase.Driver = driver;
|
||||
gameBase.Feature = [feature];
|
||||
gameBase.Device = [device];
|
||||
gameBase.Slot = [slot];
|
||||
gameBase.SoftwareList = [softwarelist];
|
||||
gameBase.RamOption = [ramoption];
|
||||
|
||||
return new Models.Listxml.Mame
|
||||
{
|
||||
Build = "XXXXXX",
|
||||
Debug = "XXXXXX",
|
||||
MameConfig = "XXXXXX",
|
||||
Game = [gameBase],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a GameBase
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.GameBase? gb)
|
||||
{
|
||||
Assert.NotNull(gb);
|
||||
Assert.Equal("XXXXXX", gb.Name);
|
||||
Assert.Equal("XXXXXX", gb.SourceFile);
|
||||
Assert.Equal("XXXXXX", gb.IsBios);
|
||||
Assert.Equal("XXXXXX", gb.IsDevice);
|
||||
Assert.Equal("XXXXXX", gb.IsMechanical);
|
||||
Assert.Equal("XXXXXX", gb.Runnable);
|
||||
Assert.Equal("XXXXXX", gb.CloneOf);
|
||||
Assert.Equal("XXXXXX", gb.RomOf);
|
||||
Assert.Equal("XXXXXX", gb.SampleOf);
|
||||
Assert.Equal("XXXXXX", gb.Description);
|
||||
Assert.Equal("XXXXXX", gb.Year);
|
||||
Assert.Equal("XXXXXX", gb.Manufacturer);
|
||||
Assert.Equal("XXXXXX", gb.History);
|
||||
|
||||
Assert.NotNull(gb.BiosSet);
|
||||
var biosset = Assert.Single(gb.BiosSet);
|
||||
Validate(biosset);
|
||||
|
||||
Assert.NotNull(gb.Rom);
|
||||
var rom = Assert.Single(gb.Rom);
|
||||
Validate(rom);
|
||||
|
||||
Assert.NotNull(gb.Disk);
|
||||
var disk = Assert.Single(gb.Disk);
|
||||
Validate(disk);
|
||||
|
||||
Assert.NotNull(gb.DeviceRef);
|
||||
var deviceref = Assert.Single(gb.DeviceRef);
|
||||
Validate(deviceref);
|
||||
|
||||
Assert.NotNull(gb.Sample);
|
||||
var sample = Assert.Single(gb.Sample);
|
||||
Validate(sample);
|
||||
|
||||
Assert.NotNull(gb.Chip);
|
||||
var chip = Assert.Single(gb.Chip);
|
||||
Validate(chip);
|
||||
|
||||
Assert.NotNull(gb.Display);
|
||||
var display = Assert.Single(gb.Display);
|
||||
Validate(display);
|
||||
|
||||
Assert.NotNull(gb.Video);
|
||||
var video = Assert.Single(gb.Video);
|
||||
Validate(video);
|
||||
|
||||
Validate(gb.Sound);
|
||||
Validate(gb.Input);
|
||||
|
||||
Assert.NotNull(gb.DipSwitch);
|
||||
var dipswitch = Assert.Single(gb.DipSwitch);
|
||||
Validate(dipswitch);
|
||||
|
||||
Assert.NotNull(gb.Configuration);
|
||||
var configuration = Assert.Single(gb.Configuration);
|
||||
Validate(configuration);
|
||||
|
||||
Assert.NotNull(gb.Port);
|
||||
var port = Assert.Single(gb.Port);
|
||||
Validate(port);
|
||||
|
||||
Assert.NotNull(gb.Adjuster);
|
||||
var adjuster = Assert.Single(gb.Adjuster);
|
||||
Validate(adjuster);
|
||||
|
||||
Validate(gb.Driver);
|
||||
|
||||
Assert.NotNull(gb.Feature);
|
||||
var feature = Assert.Single(gb.Feature);
|
||||
Validate(feature);
|
||||
|
||||
Assert.NotNull(gb.Device);
|
||||
var device = Assert.Single(gb.Device);
|
||||
Validate(device);
|
||||
|
||||
Assert.NotNull(gb.Slot);
|
||||
var slot = Assert.Single(gb.Slot);
|
||||
Validate(slot);
|
||||
|
||||
Assert.NotNull(gb.SoftwareList);
|
||||
var softwarelist = Assert.Single(gb.SoftwareList);
|
||||
Validate(softwarelist);
|
||||
|
||||
Assert.NotNull(gb.RamOption);
|
||||
var ramoption = Assert.Single(gb.RamOption);
|
||||
Validate(ramoption);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a BiosSet
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.BiosSet? biosset)
|
||||
{
|
||||
Assert.NotNull(biosset);
|
||||
Assert.Equal("XXXXXX", biosset.Name);
|
||||
Assert.Equal("XXXXXX", biosset.Description);
|
||||
Assert.Equal("XXXXXX", biosset.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Rom
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Rom? rom)
|
||||
{
|
||||
Assert.NotNull(rom);
|
||||
Assert.Equal("XXXXXX", rom.Name);
|
||||
Assert.Equal("XXXXXX", rom.Bios);
|
||||
Assert.Equal("XXXXXX", rom.Size);
|
||||
Assert.Equal("XXXXXX", rom.CRC);
|
||||
Assert.Equal("XXXXXX", rom.SHA1);
|
||||
Assert.Equal("XXXXXX", rom.Merge);
|
||||
Assert.Equal("XXXXXX", rom.Region);
|
||||
Assert.Equal("XXXXXX", rom.Offset);
|
||||
Assert.Equal("XXXXXX", rom.Status);
|
||||
Assert.Equal("XXXXXX", rom.Optional);
|
||||
Assert.Equal("XXXXXX", rom.Dispose);
|
||||
Assert.Equal("XXXXXX", rom.SoundOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Disk
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Disk? disk)
|
||||
{
|
||||
Assert.NotNull(disk);
|
||||
Assert.Equal("XXXXXX", disk.Name);
|
||||
Assert.Equal("XXXXXX", disk.MD5);
|
||||
Assert.Equal("XXXXXX", disk.SHA1);
|
||||
Assert.Equal("XXXXXX", disk.Merge);
|
||||
Assert.Equal("XXXXXX", disk.Region);
|
||||
Assert.Equal("XXXXXX", disk.Index);
|
||||
Assert.Equal("XXXXXX", disk.Writable);
|
||||
Assert.Equal("XXXXXX", disk.Status);
|
||||
Assert.Equal("XXXXXX", disk.Optional);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DeviceRef
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DeviceRef? deviceref)
|
||||
{
|
||||
Assert.NotNull(deviceref);
|
||||
Assert.Equal("XXXXXX", deviceref.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sample
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Sample? sample)
|
||||
{
|
||||
Assert.NotNull(sample);
|
||||
Assert.Equal("XXXXXX", sample.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Chip
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Chip? chip)
|
||||
{
|
||||
Assert.NotNull(chip);
|
||||
Assert.Equal("XXXXXX", chip.Name);
|
||||
Assert.Equal("XXXXXX", chip.Tag);
|
||||
Assert.Equal("XXXXXX", chip.Type);
|
||||
Assert.Equal("XXXXXX", chip.SoundOnly);
|
||||
Assert.Equal("XXXXXX", chip.Clock);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Display
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Display? display)
|
||||
{
|
||||
Assert.NotNull(display);
|
||||
Assert.Equal("XXXXXX", display.Tag);
|
||||
Assert.Equal("XXXXXX", display.Type);
|
||||
Assert.Equal("XXXXXX", display.Rotate);
|
||||
Assert.Equal("XXXXXX", display.FlipX);
|
||||
Assert.Equal("XXXXXX", display.Width);
|
||||
Assert.Equal("XXXXXX", display.Height);
|
||||
Assert.Equal("XXXXXX", display.Refresh);
|
||||
Assert.Equal("XXXXXX", display.PixClock);
|
||||
Assert.Equal("XXXXXX", display.HTotal);
|
||||
Assert.Equal("XXXXXX", display.HBEnd);
|
||||
Assert.Equal("XXXXXX", display.HBStart);
|
||||
Assert.Equal("XXXXXX", display.VTotal);
|
||||
Assert.Equal("XXXXXX", display.VBEnd);
|
||||
Assert.Equal("XXXXXX", display.VBStart);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Video
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Video? video)
|
||||
{
|
||||
Assert.NotNull(video);
|
||||
Assert.Equal("XXXXXX", video.Screen);
|
||||
Assert.Equal("XXXXXX", video.Orientation);
|
||||
Assert.Equal("XXXXXX", video.Width);
|
||||
Assert.Equal("XXXXXX", video.Height);
|
||||
Assert.Equal("XXXXXX", video.AspectX);
|
||||
Assert.Equal("XXXXXX", video.AspectY);
|
||||
Assert.Equal("XXXXXX", video.Refresh);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sound
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Sound? sound)
|
||||
{
|
||||
Assert.NotNull(sound);
|
||||
Assert.Equal("XXXXXX", sound.Channels);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Input
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Input? input)
|
||||
{
|
||||
Assert.NotNull(input);
|
||||
Assert.Equal("XXXXXX", input.Service);
|
||||
Assert.Equal("XXXXXX", input.Tilt);
|
||||
Assert.Equal("XXXXXX", input.Players);
|
||||
//Assert.Equal("XXXXXX", input.ControlAttr); // Mututally exclusive with input.Control
|
||||
Assert.Equal("XXXXXX", input.Buttons);
|
||||
Assert.Equal("XXXXXX", input.Coins);
|
||||
|
||||
Assert.NotNull(input.Control);
|
||||
var control = Assert.Single(input.Control);
|
||||
Validate(control);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Control
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Control? control)
|
||||
{
|
||||
Assert.NotNull(control);
|
||||
Assert.Equal("XXXXXX", control.Type);
|
||||
Assert.Equal("XXXXXX", control.Player);
|
||||
Assert.Equal("XXXXXX", control.Buttons);
|
||||
Assert.Equal("XXXXXX", control.ReqButtons);
|
||||
Assert.Equal("XXXXXX", control.Minimum);
|
||||
Assert.Equal("XXXXXX", control.Maximum);
|
||||
Assert.Equal("XXXXXX", control.Sensitivity);
|
||||
Assert.Equal("XXXXXX", control.KeyDelta);
|
||||
Assert.Equal("XXXXXX", control.Reverse);
|
||||
Assert.Equal("XXXXXX", control.Ways);
|
||||
Assert.Equal("XXXXXX", control.Ways2);
|
||||
Assert.Equal("XXXXXX", control.Ways3);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipSwitch
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipSwitch? dipswitch)
|
||||
{
|
||||
Assert.NotNull(dipswitch);
|
||||
Assert.Equal("XXXXXX", dipswitch.Name);
|
||||
Assert.Equal("XXXXXX", dipswitch.Tag);
|
||||
Assert.Equal("XXXXXX", dipswitch.Mask);
|
||||
Validate(dipswitch.Condition);
|
||||
|
||||
Assert.NotNull(dipswitch.DipLocation);
|
||||
var diplocation = Assert.Single(dipswitch.DipLocation);
|
||||
Validate(diplocation);
|
||||
|
||||
Assert.NotNull(dipswitch.DipValue);
|
||||
var dipvalue = Assert.Single(dipswitch.DipValue);
|
||||
Validate(dipvalue);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Condition
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Condition? condition)
|
||||
{
|
||||
Assert.NotNull(condition);
|
||||
Assert.Equal("XXXXXX", condition.Tag);
|
||||
Assert.Equal("XXXXXX", condition.Mask);
|
||||
Assert.Equal("XXXXXX", condition.Relation);
|
||||
Assert.Equal("XXXXXX", condition.Value);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipLocation
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipLocation? diplocation)
|
||||
{
|
||||
Assert.NotNull(diplocation);
|
||||
Assert.Equal("XXXXXX", diplocation.Name);
|
||||
Assert.Equal("XXXXXX", diplocation.Number);
|
||||
Assert.Equal("XXXXXX", diplocation.Inverted);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipValue
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipValue? dipvalue)
|
||||
{
|
||||
Assert.NotNull(dipvalue);
|
||||
Assert.Equal("XXXXXX", dipvalue.Name);
|
||||
Assert.Equal("XXXXXX", dipvalue.Value);
|
||||
Assert.Equal("XXXXXX", dipvalue.Default);
|
||||
Validate(dipvalue.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Configuration
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Configuration? configuration)
|
||||
{
|
||||
Assert.NotNull(configuration);
|
||||
Assert.Equal("XXXXXX", configuration.Name);
|
||||
Assert.Equal("XXXXXX", configuration.Tag);
|
||||
Assert.Equal("XXXXXX", configuration.Mask);
|
||||
Validate(configuration.Condition);
|
||||
|
||||
Assert.NotNull(configuration.ConfLocation);
|
||||
var conflocation = Assert.Single(configuration.ConfLocation);
|
||||
Validate(conflocation);
|
||||
|
||||
Assert.NotNull(configuration.ConfSetting);
|
||||
var confsetting = Assert.Single(configuration.ConfSetting);
|
||||
Validate(confsetting);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ConfLocation
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.ConfLocation? conflocation)
|
||||
{
|
||||
Assert.NotNull(conflocation);
|
||||
Assert.Equal("XXXXXX", conflocation.Name);
|
||||
Assert.Equal("XXXXXX", conflocation.Number);
|
||||
Assert.Equal("XXXXXX", conflocation.Inverted);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ConfSetting
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.ConfSetting? confsetting)
|
||||
{
|
||||
Assert.NotNull(confsetting);
|
||||
Assert.Equal("XXXXXX", confsetting.Name);
|
||||
Assert.Equal("XXXXXX", confsetting.Value);
|
||||
Assert.Equal("XXXXXX", confsetting.Default);
|
||||
Validate(confsetting.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Port
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Port? port)
|
||||
{
|
||||
Assert.NotNull(port);
|
||||
Assert.Equal("XXXXXX", port.Tag);
|
||||
|
||||
Assert.NotNull(port.Analog);
|
||||
var analog = Assert.Single(port.Analog);
|
||||
Validate(analog);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Analog
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Analog? analog)
|
||||
{
|
||||
Assert.NotNull(analog);
|
||||
Assert.Equal("XXXXXX", analog.Mask);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Adjuster
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Adjuster? adjuster)
|
||||
{
|
||||
Assert.NotNull(adjuster);
|
||||
Assert.Equal("XXXXXX", adjuster.Name);
|
||||
Assert.Equal("XXXXXX", adjuster.Default);
|
||||
Validate(adjuster.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Driver
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Driver? driver)
|
||||
{
|
||||
Assert.NotNull(driver);
|
||||
Assert.Equal("XXXXXX", driver.Status);
|
||||
Assert.Equal("XXXXXX", driver.Color);
|
||||
Assert.Equal("XXXXXX", driver.Sound);
|
||||
Assert.Equal("XXXXXX", driver.PaletteSize);
|
||||
Assert.Equal("XXXXXX", driver.Emulation);
|
||||
Assert.Equal("XXXXXX", driver.Cocktail);
|
||||
Assert.Equal("XXXXXX", driver.SaveState);
|
||||
Assert.Equal("XXXXXX", driver.RequiresArtwork);
|
||||
Assert.Equal("XXXXXX", driver.Unofficial);
|
||||
Assert.Equal("XXXXXX", driver.NoSoundHardware);
|
||||
Assert.Equal("XXXXXX", driver.Incomplete);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Feature
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Feature? feature)
|
||||
{
|
||||
Assert.NotNull(feature);
|
||||
Assert.Equal("XXXXXX", feature.Type);
|
||||
Assert.Equal("XXXXXX", feature.Status);
|
||||
Assert.Equal("XXXXXX", feature.Overall);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Device
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Device? device)
|
||||
{
|
||||
Assert.NotNull(device);
|
||||
Assert.Equal("XXXXXX", device.Type);
|
||||
Assert.Equal("XXXXXX", device.Tag);
|
||||
Assert.Equal("XXXXXX", device.FixedImage);
|
||||
Assert.Equal("XXXXXX", device.Mandatory);
|
||||
Assert.Equal("XXXXXX", device.Interface);
|
||||
Validate(device.Instance);
|
||||
|
||||
Assert.NotNull(device.Extension);
|
||||
var extension = Assert.Single(device.Extension);
|
||||
Validate(extension);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Instance
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Instance? instance)
|
||||
{
|
||||
Assert.NotNull(instance);
|
||||
Assert.Equal("XXXXXX", instance.Name);
|
||||
Assert.Equal("XXXXXX", instance.BriefName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Extension
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Extension? extension)
|
||||
{
|
||||
Assert.NotNull(extension);
|
||||
Assert.Equal("XXXXXX", extension.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Slot
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Slot? slot)
|
||||
{
|
||||
Assert.NotNull(slot);
|
||||
Assert.Equal("XXXXXX", slot.Name);
|
||||
|
||||
Assert.NotNull(slot.SlotOption);
|
||||
var slotoption = Assert.Single(slot.SlotOption);
|
||||
Validate(slotoption);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SlotOption
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.SlotOption? slotoption)
|
||||
{
|
||||
Assert.NotNull(slotoption);
|
||||
Assert.Equal("XXXXXX", slotoption.Name);
|
||||
Assert.Equal("XXXXXX", slotoption.DevName);
|
||||
Assert.Equal("XXXXXX", slotoption.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SoftwareList
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.SoftwareList? softwarelist)
|
||||
{
|
||||
Assert.NotNull(softwarelist);
|
||||
Assert.Equal("XXXXXX", softwarelist.Tag);
|
||||
Assert.Equal("XXXXXX", softwarelist.Name);
|
||||
Assert.Equal("XXXXXX", softwarelist.Status);
|
||||
Assert.Equal("XXXXXX", softwarelist.Filter);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a RamOption
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.RamOption? ramoption)
|
||||
{
|
||||
Assert.NotNull(ramoption);
|
||||
Assert.Equal("XXXXXX", ramoption.Name);
|
||||
Assert.Equal("XXXXXX", ramoption.Default);
|
||||
Assert.Equal("XXXXXX", ramoption.Content);
|
||||
}
|
||||
}
|
||||
}
|
||||
562
SabreTools.Serialization.Test/CrossModel/LogiqxTests.cs
Normal file
562
SabreTools.Serialization.Test/CrossModel/LogiqxTests.cs
Normal file
@@ -0,0 +1,562 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class LogiqxTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripGameTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Logiqx();
|
||||
|
||||
// Build the data
|
||||
Models.Logiqx.Datafile df = Build(game: true);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(df);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Logiqx.Datafile? newDf = serializer.Deserialize(metadata, game: true);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newDf);
|
||||
Assert.Equal("XXXXXX", newDf.Build);
|
||||
Assert.Equal("XXXXXX", newDf.Debug);
|
||||
Assert.Equal("XXXXXX", newDf.SchemaLocation);
|
||||
Validate(newDf.Header);
|
||||
|
||||
Assert.NotNull(newDf.Game);
|
||||
Assert.Equal(2, newDf.Game.Length);
|
||||
Validate(newDf.Game[0], nested: false);
|
||||
Validate(newDf.Game[1], nested: true);
|
||||
|
||||
// TODO: Unsupported for round-trip
|
||||
Assert.Null(newDf.Dir);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMachineTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Logiqx();
|
||||
|
||||
// Build the data
|
||||
Models.Logiqx.Datafile df = Build(game: false);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(df);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Logiqx.Datafile? newDf = serializer.Deserialize(metadata, game: false);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newDf);
|
||||
Assert.Equal("XXXXXX", newDf.Build);
|
||||
Assert.Equal("XXXXXX", newDf.Debug);
|
||||
Assert.Equal("XXXXXX", newDf.SchemaLocation);
|
||||
Validate(newDf.Header);
|
||||
|
||||
Assert.NotNull(newDf.Game);
|
||||
Assert.Equal(2, newDf.Game.Length);
|
||||
Validate(newDf.Game[0], nested: false);
|
||||
Validate(newDf.Game[1], nested: true);
|
||||
|
||||
// TODO: Unsupported for round-trip
|
||||
Assert.Null(newDf.Dir);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.Logiqx.Datafile Build(bool game)
|
||||
{
|
||||
var clrmamepro = new Models.Logiqx.ClrMamePro
|
||||
{
|
||||
Header = "XXXXXX",
|
||||
ForceMerging = "XXXXXX",
|
||||
ForceNodump = "XXXXXX",
|
||||
ForcePacking = "XXXXXX",
|
||||
};
|
||||
|
||||
var romcenter = new Models.Logiqx.RomCenter
|
||||
{
|
||||
Plugin = "XXXXXX",
|
||||
RomMode = "XXXXXX",
|
||||
BiosMode = "XXXXXX",
|
||||
SampleMode = "XXXXXX",
|
||||
LockRomMode = "XXXXXX",
|
||||
LockBiosMode = "XXXXXX",
|
||||
LockSampleMode = "XXXXXX",
|
||||
};
|
||||
|
||||
var header = new Models.Logiqx.Header
|
||||
{
|
||||
Id = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
RootDir = "XXXXXX",
|
||||
Category = "XXXXXX",
|
||||
Version = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
Author = "XXXXXX",
|
||||
Email = "XXXXXX",
|
||||
Homepage = "XXXXXX",
|
||||
Url = "XXXXXX",
|
||||
Comment = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
ClrMamePro = clrmamepro,
|
||||
RomCenter = romcenter,
|
||||
};
|
||||
|
||||
var trurip = new Models.Logiqx.Trurip
|
||||
{
|
||||
TitleID = "XXXXXX",
|
||||
Publisher = "XXXXXX",
|
||||
Developer = "XXXXXX",
|
||||
Year = "XXXXXX",
|
||||
Genre = "XXXXXX",
|
||||
Subgenre = "XXXXXX",
|
||||
Ratings = "XXXXXX",
|
||||
Score = "XXXXXX",
|
||||
Players = "XXXXXX",
|
||||
Enabled = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
Source = "XXXXXX",
|
||||
CloneOf = "XXXXXX",
|
||||
RelatedTo = "XXXXXX",
|
||||
};
|
||||
|
||||
var release = new Models.Logiqx.Release
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Language = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var biosset = new Models.Logiqx.BiosSet
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var rom = new Models.Logiqx.Rom
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
SHA256 = "XXXXXX",
|
||||
SHA384 = "XXXXXX",
|
||||
SHA512 = "XXXXXX",
|
||||
SpamSum = "XXXXXX",
|
||||
xxHash364 = "XXXXXX",
|
||||
xxHash3128 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Serial = "XXXXXX",
|
||||
Header = "XXXXXX",
|
||||
Date = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
MIA = "XXXXXX",
|
||||
};
|
||||
|
||||
var disk = new Models.Logiqx.Disk
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
};
|
||||
|
||||
var media = new Models.Logiqx.Media
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
SHA256 = "XXXXXX",
|
||||
SpamSum = "XXXXXX",
|
||||
};
|
||||
|
||||
var deviceRef = new Models.Logiqx.DeviceRef
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var sample = new Models.Logiqx.Sample
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var archive = new Models.Logiqx.Archive
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var driver = new Models.Logiqx.Driver
|
||||
{
|
||||
Status = "XXXXXX",
|
||||
Emulation = "XXXXXX",
|
||||
Cocktail = "XXXXXX",
|
||||
SaveState = "XXXXXX",
|
||||
RequiresArtwork = "XXXXXX",
|
||||
Unofficial = "XXXXXX",
|
||||
NoSoundHardware = "XXXXXX",
|
||||
Incomplete = "XXXXXX",
|
||||
};
|
||||
|
||||
var softwarelist = new Models.Logiqx.SoftwareList
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Filter = "XXXXXX",
|
||||
};
|
||||
|
||||
Models.Logiqx.GameBase gameBase = game
|
||||
? new Models.Logiqx.Game()
|
||||
: new Models.Logiqx.Machine();
|
||||
gameBase.Name = "XXXXXX";
|
||||
gameBase.SourceFile = "XXXXXX";
|
||||
gameBase.IsBios = "XXXXXX";
|
||||
gameBase.IsDevice = "XXXXXX";
|
||||
gameBase.IsMechanical = "XXXXXX";
|
||||
gameBase.CloneOf = "XXXXXX";
|
||||
gameBase.RomOf = "XXXXXX";
|
||||
gameBase.SampleOf = "XXXXXX";
|
||||
gameBase.Board = "XXXXXX";
|
||||
gameBase.RebuildTo = "XXXXXX";
|
||||
gameBase.Id = "XXXXXX";
|
||||
gameBase.CloneOfId = "XXXXXX";
|
||||
gameBase.Runnable = "XXXXXX";
|
||||
gameBase.Comment = ["XXXXXX"];
|
||||
gameBase.Description = "XXXXXX";
|
||||
gameBase.Year = "XXXXXX";
|
||||
gameBase.Manufacturer = "XXXXXX";
|
||||
gameBase.Publisher = "XXXXXX";
|
||||
gameBase.Category = ["XXXXXX"];
|
||||
gameBase.Trurip = trurip;
|
||||
gameBase.Release = [release];
|
||||
gameBase.BiosSet = [biosset];
|
||||
gameBase.Rom = [rom];
|
||||
gameBase.Disk = [disk];
|
||||
gameBase.Media = [media];
|
||||
gameBase.DeviceRef = [deviceRef];
|
||||
gameBase.Sample = [sample];
|
||||
gameBase.Archive = [archive];
|
||||
gameBase.Driver = driver;
|
||||
gameBase.SoftwareList = [softwarelist];
|
||||
|
||||
var subdir = new Models.Logiqx.Dir
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Game = [gameBase],
|
||||
};
|
||||
|
||||
var dir = new Models.Logiqx.Dir
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Subdir = [subdir],
|
||||
};
|
||||
|
||||
return new Models.Logiqx.Datafile
|
||||
{
|
||||
Build = "XXXXXX",
|
||||
Debug = "XXXXXX",
|
||||
SchemaLocation = "XXXXXX",
|
||||
Header = header,
|
||||
Game = [gameBase],
|
||||
Dir = [dir],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Header
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Header? header)
|
||||
{
|
||||
Assert.NotNull(header);
|
||||
Assert.Equal("XXXXXX", header.Id);
|
||||
Assert.Equal("XXXXXX", header.Name);
|
||||
Assert.Equal("XXXXXX", header.Description);
|
||||
Assert.Equal("XXXXXX", header.RootDir);
|
||||
Assert.Equal("XXXXXX", header.Category);
|
||||
Assert.Equal("XXXXXX", header.Version);
|
||||
Assert.Equal("XXXXXX", header.Date);
|
||||
Assert.Equal("XXXXXX", header.Author);
|
||||
Assert.Equal("XXXXXX", header.Email);
|
||||
Assert.Equal("XXXXXX", header.Homepage);
|
||||
Assert.Equal("XXXXXX", header.Url);
|
||||
Assert.Equal("XXXXXX", header.Comment);
|
||||
Assert.Equal("XXXXXX", header.Type);
|
||||
Validate(header.ClrMamePro);
|
||||
Validate(header.RomCenter);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ClrMamePro
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.ClrMamePro? cmp)
|
||||
{
|
||||
Assert.NotNull(cmp);
|
||||
Assert.Equal("XXXXXX", cmp.Header);
|
||||
Assert.Equal("XXXXXX", cmp.ForceMerging);
|
||||
Assert.Equal("XXXXXX", cmp.ForceNodump);
|
||||
Assert.Equal("XXXXXX", cmp.ForcePacking);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a RomCenter
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.RomCenter? rc)
|
||||
{
|
||||
Assert.NotNull(rc);
|
||||
Assert.Equal("XXXXXX", rc.Plugin);
|
||||
Assert.Equal("XXXXXX", rc.RomMode);
|
||||
Assert.Equal("XXXXXX", rc.BiosMode);
|
||||
Assert.Equal("XXXXXX", rc.SampleMode);
|
||||
Assert.Equal("XXXXXX", rc.LockRomMode);
|
||||
Assert.Equal("XXXXXX", rc.LockBiosMode);
|
||||
Assert.Equal("XXXXXX", rc.LockSampleMode);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a GameBase
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.GameBase? gb, bool nested)
|
||||
{
|
||||
Assert.NotNull(gb);
|
||||
if (nested)
|
||||
Assert.Equal("XXXXXX\\XXXXXX\\XXXXXX", gb.Name);
|
||||
else
|
||||
Assert.Equal("XXXXXX", gb.Name);
|
||||
Assert.Equal("XXXXXX", gb.SourceFile);
|
||||
Assert.Equal("XXXXXX", gb.IsBios);
|
||||
Assert.Equal("XXXXXX", gb.IsDevice);
|
||||
Assert.Equal("XXXXXX", gb.IsMechanical);
|
||||
Assert.Equal("XXXXXX", gb.CloneOf);
|
||||
Assert.Equal("XXXXXX", gb.RomOf);
|
||||
Assert.Equal("XXXXXX", gb.SampleOf);
|
||||
Assert.Equal("XXXXXX", gb.Board);
|
||||
Assert.Equal("XXXXXX", gb.RebuildTo);
|
||||
Assert.Equal("XXXXXX", gb.Id);
|
||||
Assert.Equal("XXXXXX", gb.CloneOfId);
|
||||
Assert.Equal("XXXXXX", gb.Runnable);
|
||||
|
||||
Assert.NotNull(gb.Comment);
|
||||
string comment = Assert.Single(gb.Comment);
|
||||
Assert.Equal("XXXXXX", comment);
|
||||
|
||||
Assert.Equal("XXXXXX", gb.Description);
|
||||
Assert.Equal("XXXXXX", gb.Year);
|
||||
Assert.Equal("XXXXXX", gb.Manufacturer);
|
||||
Assert.Equal("XXXXXX", gb.Publisher);
|
||||
|
||||
Assert.NotNull(gb.Category);
|
||||
string category = Assert.Single(gb.Category);
|
||||
Assert.Equal("XXXXXX", category);
|
||||
|
||||
Validate(gb.Trurip);
|
||||
|
||||
Assert.NotNull(gb.Release);
|
||||
var release = Assert.Single(gb.Release);
|
||||
Validate(release);
|
||||
|
||||
Assert.NotNull(gb.BiosSet);
|
||||
var biosset = Assert.Single(gb.BiosSet);
|
||||
Validate(biosset);
|
||||
|
||||
Assert.NotNull(gb.Rom);
|
||||
var rom = Assert.Single(gb.Rom);
|
||||
Validate(rom);
|
||||
|
||||
Assert.NotNull(gb.Disk);
|
||||
var disk = Assert.Single(gb.Disk);
|
||||
Validate(disk);
|
||||
|
||||
Assert.NotNull(gb.Media);
|
||||
var media = Assert.Single(gb.Media);
|
||||
Validate(media);
|
||||
|
||||
Assert.NotNull(gb.DeviceRef);
|
||||
var deviceref = Assert.Single(gb.DeviceRef);
|
||||
Validate(deviceref);
|
||||
|
||||
Assert.NotNull(gb.Sample);
|
||||
var sample = Assert.Single(gb.Sample);
|
||||
Validate(sample);
|
||||
|
||||
Assert.NotNull(gb.Archive);
|
||||
var archive = Assert.Single(gb.Archive);
|
||||
Validate(archive);
|
||||
|
||||
Validate(gb.Driver);
|
||||
|
||||
Assert.NotNull(gb.SoftwareList);
|
||||
var softwarelist = Assert.Single(gb.SoftwareList);
|
||||
Validate(softwarelist);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Trurip
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Trurip? trurip)
|
||||
{
|
||||
Assert.NotNull(trurip);
|
||||
Assert.Equal("XXXXXX", trurip.TitleID);
|
||||
Assert.Equal("XXXXXX", trurip.Publisher);
|
||||
Assert.Equal("XXXXXX", trurip.Developer);
|
||||
Assert.Equal("XXXXXX", trurip.Year);
|
||||
Assert.Equal("XXXXXX", trurip.Genre);
|
||||
Assert.Equal("XXXXXX", trurip.Subgenre);
|
||||
Assert.Equal("XXXXXX", trurip.Ratings);
|
||||
Assert.Equal("XXXXXX", trurip.Score);
|
||||
Assert.Equal("XXXXXX", trurip.Players);
|
||||
Assert.Equal("XXXXXX", trurip.Enabled);
|
||||
Assert.Equal("XXXXXX", trurip.CRC);
|
||||
Assert.Equal("XXXXXX", trurip.Source);
|
||||
Assert.Equal("XXXXXX", trurip.CloneOf);
|
||||
Assert.Equal("XXXXXX", trurip.RelatedTo);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Release
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Release? release)
|
||||
{
|
||||
Assert.NotNull(release);
|
||||
Assert.Equal("XXXXXX", release.Name);
|
||||
Assert.Equal("XXXXXX", release.Region);
|
||||
Assert.Equal("XXXXXX", release.Language);
|
||||
Assert.Equal("XXXXXX", release.Date);
|
||||
Assert.Equal("XXXXXX", release.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a BiosSet
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.BiosSet? biosset)
|
||||
{
|
||||
Assert.NotNull(biosset);
|
||||
Assert.Equal("XXXXXX", biosset.Name);
|
||||
Assert.Equal("XXXXXX", biosset.Description);
|
||||
Assert.Equal("XXXXXX", biosset.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Rom
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Rom? rom)
|
||||
{
|
||||
Assert.NotNull(rom);
|
||||
Assert.Equal("XXXXXX", rom.Name);
|
||||
Assert.Equal("XXXXXX", rom.Size);
|
||||
Assert.Equal("XXXXXX", rom.CRC);
|
||||
Assert.Equal("XXXXXX", rom.MD5);
|
||||
Assert.Equal("XXXXXX", rom.SHA1);
|
||||
Assert.Equal("XXXXXX", rom.SHA256);
|
||||
Assert.Equal("XXXXXX", rom.SHA384);
|
||||
Assert.Equal("XXXXXX", rom.SHA512);
|
||||
Assert.Equal("XXXXXX", rom.SpamSum);
|
||||
Assert.Equal("XXXXXX", rom.xxHash364);
|
||||
Assert.Equal("XXXXXX", rom.xxHash3128);
|
||||
Assert.Equal("XXXXXX", rom.Merge);
|
||||
Assert.Equal("XXXXXX", rom.Status);
|
||||
Assert.Equal("XXXXXX", rom.Serial);
|
||||
Assert.Equal("XXXXXX", rom.Header);
|
||||
Assert.Equal("XXXXXX", rom.Date);
|
||||
Assert.Equal("XXXXXX", rom.Inverted);
|
||||
Assert.Equal("XXXXXX", rom.MIA);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Disk
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Disk? disk)
|
||||
{
|
||||
Assert.NotNull(disk);
|
||||
Assert.Equal("XXXXXX", disk.Name);
|
||||
Assert.Equal("XXXXXX", disk.MD5);
|
||||
Assert.Equal("XXXXXX", disk.SHA1);
|
||||
Assert.Equal("XXXXXX", disk.Merge);
|
||||
Assert.Equal("XXXXXX", disk.Status);
|
||||
Assert.Equal("XXXXXX", disk.Region);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Media
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Media? media)
|
||||
{
|
||||
Assert.NotNull(media);
|
||||
Assert.Equal("XXXXXX", media.Name);
|
||||
Assert.Equal("XXXXXX", media.MD5);
|
||||
Assert.Equal("XXXXXX", media.SHA1);
|
||||
Assert.Equal("XXXXXX", media.SHA256);
|
||||
Assert.Equal("XXXXXX", media.SpamSum);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DeviceRef
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.DeviceRef? deviceref)
|
||||
{
|
||||
Assert.NotNull(deviceref);
|
||||
Assert.Equal("XXXXXX", deviceref.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sample
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Sample? sample)
|
||||
{
|
||||
Assert.NotNull(sample);
|
||||
Assert.Equal("XXXXXX", sample.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Archive
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Archive? archive)
|
||||
{
|
||||
Assert.NotNull(archive);
|
||||
Assert.Equal("XXXXXX", archive.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Driver
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.Driver? driver)
|
||||
{
|
||||
Assert.NotNull(driver);
|
||||
Assert.Equal("XXXXXX", driver.Status);
|
||||
Assert.Equal("XXXXXX", driver.Emulation);
|
||||
Assert.Equal("XXXXXX", driver.Cocktail);
|
||||
Assert.Equal("XXXXXX", driver.SaveState);
|
||||
Assert.Equal("XXXXXX", driver.RequiresArtwork);
|
||||
Assert.Equal("XXXXXX", driver.Unofficial);
|
||||
Assert.Equal("XXXXXX", driver.NoSoundHardware);
|
||||
Assert.Equal("XXXXXX", driver.Incomplete);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SoftwareList
|
||||
/// </summary>
|
||||
private static void Validate(Models.Logiqx.SoftwareList? softwarelist)
|
||||
{
|
||||
Assert.NotNull(softwarelist);
|
||||
Assert.Equal("XXXXXX", softwarelist.Tag);
|
||||
Assert.Equal("XXXXXX", softwarelist.Name);
|
||||
Assert.Equal("XXXXXX", softwarelist.Status);
|
||||
Assert.Equal("XXXXXX", softwarelist.Filter);
|
||||
}
|
||||
}
|
||||
}
|
||||
872
SabreTools.Serialization.Test/CrossModel/M1Tests.cs
Normal file
872
SabreTools.Serialization.Test/CrossModel/M1Tests.cs
Normal file
@@ -0,0 +1,872 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class M1Tests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripGameTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.M1();
|
||||
|
||||
// Build the data
|
||||
Models.Listxml.M1 m1 = Build(game: true);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(m1);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listxml.M1? newM1 = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newM1);
|
||||
Assert.Equal("XXXXXX", newM1.Version);
|
||||
|
||||
Assert.NotNull(newM1.Game);
|
||||
var newGame = Assert.Single(newM1.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMachineTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.M1();
|
||||
|
||||
// Build the data
|
||||
Models.Listxml.M1 m1 = Build(game: false);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(m1);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listxml.M1? newM1 = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newM1);
|
||||
Assert.Equal("XXXXXX", newM1.Version);
|
||||
|
||||
Assert.NotNull(newM1.Game);
|
||||
var newGame = Assert.Single(newM1.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.Listxml.M1 Build(bool game)
|
||||
{
|
||||
var biosset = new Models.Listxml.BiosSet
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var rom = new Models.Listxml.Rom
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Bios = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Offset = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Optional = "XXXXXX",
|
||||
Dispose = "XXXXXX",
|
||||
SoundOnly = "XXXXXX",
|
||||
};
|
||||
|
||||
var disk = new Models.Listxml.Disk
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Index = "XXXXXX",
|
||||
Writable = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Optional = "XXXXXX",
|
||||
};
|
||||
|
||||
var deviceref = new Models.Listxml.DeviceRef
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var sample = new Models.Listxml.Sample
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var chip = new Models.Listxml.Chip
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
SoundOnly = "XXXXXX",
|
||||
Clock = "XXXXXX",
|
||||
};
|
||||
|
||||
var display = new Models.Listxml.Display
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
Rotate = "XXXXXX",
|
||||
FlipX = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
Refresh = "XXXXXX",
|
||||
PixClock = "XXXXXX",
|
||||
HTotal = "XXXXXX",
|
||||
HBEnd = "XXXXXX",
|
||||
HBStart = "XXXXXX",
|
||||
VTotal = "XXXXXX",
|
||||
VBEnd = "XXXXXX",
|
||||
VBStart = "XXXXXX",
|
||||
};
|
||||
|
||||
var video = new Models.Listxml.Video
|
||||
{
|
||||
Screen = "XXXXXX",
|
||||
Orientation = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
AspectX = "XXXXXX",
|
||||
AspectY = "XXXXXX",
|
||||
Refresh = "XXXXXX",
|
||||
};
|
||||
|
||||
var sound = new Models.Listxml.Sound
|
||||
{
|
||||
Channels = "XXXXXX",
|
||||
};
|
||||
|
||||
var control = new Models.Listxml.Control
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Player = "XXXXXX",
|
||||
Buttons = "XXXXXX",
|
||||
ReqButtons = "XXXXXX",
|
||||
Minimum = "XXXXXX",
|
||||
Maximum = "XXXXXX",
|
||||
Sensitivity = "XXXXXX",
|
||||
KeyDelta = "XXXXXX",
|
||||
Reverse = "XXXXXX",
|
||||
Ways = "XXXXXX",
|
||||
Ways2 = "XXXXXX",
|
||||
Ways3 = "XXXXXX",
|
||||
};
|
||||
|
||||
var input = new Models.Listxml.Input
|
||||
{
|
||||
Service = "XXXXXX",
|
||||
Tilt = "XXXXXX",
|
||||
Players = "XXXXXX",
|
||||
//ControlAttr = "XXXXXX", // Mututally exclusive with input.Control
|
||||
Buttons = "XXXXXX",
|
||||
Coins = "XXXXXX",
|
||||
Control = [control],
|
||||
};
|
||||
|
||||
var condition = new Models.Listxml.Condition
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Relation = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
};
|
||||
|
||||
var diplocation = new Models.Listxml.DipLocation
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Number = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
};
|
||||
|
||||
var dipvalue = new Models.Listxml.DipValue
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var dipswitch = new Models.Listxml.DipSwitch
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Condition = condition,
|
||||
DipLocation = [diplocation],
|
||||
DipValue = [dipvalue],
|
||||
};
|
||||
|
||||
var conflocation = new Models.Listxml.ConfLocation
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Number = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
};
|
||||
|
||||
var confsetting = new Models.Listxml.ConfSetting
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var configuration = new Models.Listxml.Configuration
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Condition = condition,
|
||||
ConfLocation = [conflocation],
|
||||
ConfSetting = [confsetting],
|
||||
};
|
||||
|
||||
var analog = new Models.Listxml.Analog
|
||||
{
|
||||
Mask = "XXXXXX",
|
||||
};
|
||||
|
||||
var port = new Models.Listxml.Port
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Analog = [analog],
|
||||
};
|
||||
|
||||
var adjuster = new Models.Listxml.Adjuster
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var driver = new Models.Listxml.Driver
|
||||
{
|
||||
Status = "XXXXXX",
|
||||
Color = "XXXXXX",
|
||||
Sound = "XXXXXX",
|
||||
PaletteSize = "XXXXXX",
|
||||
Emulation = "XXXXXX",
|
||||
Cocktail = "XXXXXX",
|
||||
SaveState = "XXXXXX",
|
||||
RequiresArtwork = "XXXXXX",
|
||||
Unofficial = "XXXXXX",
|
||||
NoSoundHardware = "XXXXXX",
|
||||
Incomplete = "XXXXXX",
|
||||
};
|
||||
|
||||
var feature = new Models.Listxml.Feature
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Overall = "XXXXXX",
|
||||
};
|
||||
|
||||
var instance = new Models.Listxml.Instance
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
BriefName = "XXXXXX",
|
||||
};
|
||||
|
||||
var extension = new Models.Listxml.Extension
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var device = new Models.Listxml.Device
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
FixedImage = "XXXXXX",
|
||||
Mandatory = "XXXXXX",
|
||||
Interface = "XXXXXX",
|
||||
Instance = instance,
|
||||
Extension = [extension],
|
||||
};
|
||||
|
||||
var slotOption = new Models.Listxml.SlotOption
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
DevName = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var slot = new Models.Listxml.Slot
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
SlotOption = [slotOption],
|
||||
};
|
||||
|
||||
var softwarelist = new Models.Listxml.SoftwareList
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Filter = "XXXXXX",
|
||||
};
|
||||
|
||||
var ramoption = new Models.Listxml.RamOption
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Content = "XXXXXX",
|
||||
};
|
||||
|
||||
Models.Listxml.GameBase gameBase = game
|
||||
? new Models.Listxml.Game()
|
||||
: new Models.Listxml.Machine();
|
||||
gameBase.Name = "XXXXXX";
|
||||
gameBase.SourceFile = "XXXXXX";
|
||||
gameBase.IsBios = "XXXXXX";
|
||||
gameBase.IsDevice = "XXXXXX";
|
||||
gameBase.IsMechanical = "XXXXXX";
|
||||
gameBase.Runnable = "XXXXXX";
|
||||
gameBase.CloneOf = "XXXXXX";
|
||||
gameBase.RomOf = "XXXXXX";
|
||||
gameBase.SampleOf = "XXXXXX";
|
||||
gameBase.Description = "XXXXXX";
|
||||
gameBase.Year = "XXXXXX";
|
||||
gameBase.Manufacturer = "XXXXXX";
|
||||
gameBase.History = "XXXXXX";
|
||||
gameBase.BiosSet = [biosset];
|
||||
gameBase.Rom = [rom];
|
||||
gameBase.Disk = [disk];
|
||||
gameBase.DeviceRef = [deviceref];
|
||||
gameBase.Sample = [sample];
|
||||
gameBase.Chip = [chip];
|
||||
gameBase.Display = [display];
|
||||
gameBase.Video = [video];
|
||||
gameBase.Sound = sound;
|
||||
gameBase.Input = input;
|
||||
gameBase.DipSwitch = [dipswitch];
|
||||
gameBase.Configuration = [configuration];
|
||||
gameBase.Port = [port];
|
||||
gameBase.Adjuster = [adjuster];
|
||||
gameBase.Driver = driver;
|
||||
gameBase.Feature = [feature];
|
||||
gameBase.Device = [device];
|
||||
gameBase.Slot = [slot];
|
||||
gameBase.SoftwareList = [softwarelist];
|
||||
gameBase.RamOption = [ramoption];
|
||||
|
||||
return new Models.Listxml.M1
|
||||
{
|
||||
Version = "XXXXXX",
|
||||
Game = [gameBase],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a GameBase
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.GameBase? gb)
|
||||
{
|
||||
Assert.NotNull(gb);
|
||||
Assert.Equal("XXXXXX", gb.Name);
|
||||
Assert.Equal("XXXXXX", gb.SourceFile);
|
||||
Assert.Equal("XXXXXX", gb.IsBios);
|
||||
Assert.Equal("XXXXXX", gb.IsDevice);
|
||||
Assert.Equal("XXXXXX", gb.IsMechanical);
|
||||
Assert.Equal("XXXXXX", gb.Runnable);
|
||||
Assert.Equal("XXXXXX", gb.CloneOf);
|
||||
Assert.Equal("XXXXXX", gb.RomOf);
|
||||
Assert.Equal("XXXXXX", gb.SampleOf);
|
||||
Assert.Equal("XXXXXX", gb.Description);
|
||||
Assert.Equal("XXXXXX", gb.Year);
|
||||
Assert.Equal("XXXXXX", gb.Manufacturer);
|
||||
Assert.Equal("XXXXXX", gb.History);
|
||||
|
||||
Assert.NotNull(gb.BiosSet);
|
||||
var biosset = Assert.Single(gb.BiosSet);
|
||||
Validate(biosset);
|
||||
|
||||
Assert.NotNull(gb.Rom);
|
||||
var rom = Assert.Single(gb.Rom);
|
||||
Validate(rom);
|
||||
|
||||
Assert.NotNull(gb.Disk);
|
||||
var disk = Assert.Single(gb.Disk);
|
||||
Validate(disk);
|
||||
|
||||
Assert.NotNull(gb.DeviceRef);
|
||||
var deviceref = Assert.Single(gb.DeviceRef);
|
||||
Validate(deviceref);
|
||||
|
||||
Assert.NotNull(gb.Sample);
|
||||
var sample = Assert.Single(gb.Sample);
|
||||
Validate(sample);
|
||||
|
||||
Assert.NotNull(gb.Chip);
|
||||
var chip = Assert.Single(gb.Chip);
|
||||
Validate(chip);
|
||||
|
||||
Assert.NotNull(gb.Display);
|
||||
var display = Assert.Single(gb.Display);
|
||||
Validate(display);
|
||||
|
||||
Assert.NotNull(gb.Video);
|
||||
var video = Assert.Single(gb.Video);
|
||||
Validate(video);
|
||||
|
||||
Validate(gb.Sound);
|
||||
Validate(gb.Input);
|
||||
|
||||
Assert.NotNull(gb.DipSwitch);
|
||||
var dipswitch = Assert.Single(gb.DipSwitch);
|
||||
Validate(dipswitch);
|
||||
|
||||
Assert.NotNull(gb.Configuration);
|
||||
var configuration = Assert.Single(gb.Configuration);
|
||||
Validate(configuration);
|
||||
|
||||
Assert.NotNull(gb.Port);
|
||||
var port = Assert.Single(gb.Port);
|
||||
Validate(port);
|
||||
|
||||
Assert.NotNull(gb.Adjuster);
|
||||
var adjuster = Assert.Single(gb.Adjuster);
|
||||
Validate(adjuster);
|
||||
|
||||
Validate(gb.Driver);
|
||||
|
||||
Assert.NotNull(gb.Feature);
|
||||
var feature = Assert.Single(gb.Feature);
|
||||
Validate(feature);
|
||||
|
||||
Assert.NotNull(gb.Device);
|
||||
var device = Assert.Single(gb.Device);
|
||||
Validate(device);
|
||||
|
||||
Assert.NotNull(gb.Slot);
|
||||
var slot = Assert.Single(gb.Slot);
|
||||
Validate(slot);
|
||||
|
||||
Assert.NotNull(gb.SoftwareList);
|
||||
var softwarelist = Assert.Single(gb.SoftwareList);
|
||||
Validate(softwarelist);
|
||||
|
||||
Assert.NotNull(gb.RamOption);
|
||||
var ramoption = Assert.Single(gb.RamOption);
|
||||
Validate(ramoption);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a BiosSet
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.BiosSet? biosset)
|
||||
{
|
||||
Assert.NotNull(biosset);
|
||||
Assert.Equal("XXXXXX", biosset.Name);
|
||||
Assert.Equal("XXXXXX", biosset.Description);
|
||||
Assert.Equal("XXXXXX", biosset.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Rom
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Rom? rom)
|
||||
{
|
||||
Assert.NotNull(rom);
|
||||
Assert.Equal("XXXXXX", rom.Name);
|
||||
Assert.Equal("XXXXXX", rom.Bios);
|
||||
Assert.Equal("XXXXXX", rom.Size);
|
||||
Assert.Equal("XXXXXX", rom.CRC);
|
||||
Assert.Equal("XXXXXX", rom.SHA1);
|
||||
Assert.Equal("XXXXXX", rom.Merge);
|
||||
Assert.Equal("XXXXXX", rom.Region);
|
||||
Assert.Equal("XXXXXX", rom.Offset);
|
||||
Assert.Equal("XXXXXX", rom.Status);
|
||||
Assert.Equal("XXXXXX", rom.Optional);
|
||||
Assert.Equal("XXXXXX", rom.Dispose);
|
||||
Assert.Equal("XXXXXX", rom.SoundOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Disk
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Disk? disk)
|
||||
{
|
||||
Assert.NotNull(disk);
|
||||
Assert.Equal("XXXXXX", disk.Name);
|
||||
Assert.Equal("XXXXXX", disk.MD5);
|
||||
Assert.Equal("XXXXXX", disk.SHA1);
|
||||
Assert.Equal("XXXXXX", disk.Merge);
|
||||
Assert.Equal("XXXXXX", disk.Region);
|
||||
Assert.Equal("XXXXXX", disk.Index);
|
||||
Assert.Equal("XXXXXX", disk.Writable);
|
||||
Assert.Equal("XXXXXX", disk.Status);
|
||||
Assert.Equal("XXXXXX", disk.Optional);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DeviceRef
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DeviceRef? deviceref)
|
||||
{
|
||||
Assert.NotNull(deviceref);
|
||||
Assert.Equal("XXXXXX", deviceref.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sample
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Sample? sample)
|
||||
{
|
||||
Assert.NotNull(sample);
|
||||
Assert.Equal("XXXXXX", sample.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Chip
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Chip? chip)
|
||||
{
|
||||
Assert.NotNull(chip);
|
||||
Assert.Equal("XXXXXX", chip.Name);
|
||||
Assert.Equal("XXXXXX", chip.Tag);
|
||||
Assert.Equal("XXXXXX", chip.Type);
|
||||
Assert.Equal("XXXXXX", chip.SoundOnly);
|
||||
Assert.Equal("XXXXXX", chip.Clock);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Display
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Display? display)
|
||||
{
|
||||
Assert.NotNull(display);
|
||||
Assert.Equal("XXXXXX", display.Tag);
|
||||
Assert.Equal("XXXXXX", display.Type);
|
||||
Assert.Equal("XXXXXX", display.Rotate);
|
||||
Assert.Equal("XXXXXX", display.FlipX);
|
||||
Assert.Equal("XXXXXX", display.Width);
|
||||
Assert.Equal("XXXXXX", display.Height);
|
||||
Assert.Equal("XXXXXX", display.Refresh);
|
||||
Assert.Equal("XXXXXX", display.PixClock);
|
||||
Assert.Equal("XXXXXX", display.HTotal);
|
||||
Assert.Equal("XXXXXX", display.HBEnd);
|
||||
Assert.Equal("XXXXXX", display.HBStart);
|
||||
Assert.Equal("XXXXXX", display.VTotal);
|
||||
Assert.Equal("XXXXXX", display.VBEnd);
|
||||
Assert.Equal("XXXXXX", display.VBStart);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Video
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Video? video)
|
||||
{
|
||||
Assert.NotNull(video);
|
||||
Assert.Equal("XXXXXX", video.Screen);
|
||||
Assert.Equal("XXXXXX", video.Orientation);
|
||||
Assert.Equal("XXXXXX", video.Width);
|
||||
Assert.Equal("XXXXXX", video.Height);
|
||||
Assert.Equal("XXXXXX", video.AspectX);
|
||||
Assert.Equal("XXXXXX", video.AspectY);
|
||||
Assert.Equal("XXXXXX", video.Refresh);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sound
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Sound? sound)
|
||||
{
|
||||
Assert.NotNull(sound);
|
||||
Assert.Equal("XXXXXX", sound.Channels);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Input
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Input? input)
|
||||
{
|
||||
Assert.NotNull(input);
|
||||
Assert.Equal("XXXXXX", input.Service);
|
||||
Assert.Equal("XXXXXX", input.Tilt);
|
||||
Assert.Equal("XXXXXX", input.Players);
|
||||
//Assert.Equal("XXXXXX", input.ControlAttr); // Mututally exclusive with input.Control
|
||||
Assert.Equal("XXXXXX", input.Buttons);
|
||||
Assert.Equal("XXXXXX", input.Coins);
|
||||
|
||||
Assert.NotNull(input.Control);
|
||||
var control = Assert.Single(input.Control);
|
||||
Validate(control);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Control
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Control? control)
|
||||
{
|
||||
Assert.NotNull(control);
|
||||
Assert.Equal("XXXXXX", control.Type);
|
||||
Assert.Equal("XXXXXX", control.Player);
|
||||
Assert.Equal("XXXXXX", control.Buttons);
|
||||
Assert.Equal("XXXXXX", control.ReqButtons);
|
||||
Assert.Equal("XXXXXX", control.Minimum);
|
||||
Assert.Equal("XXXXXX", control.Maximum);
|
||||
Assert.Equal("XXXXXX", control.Sensitivity);
|
||||
Assert.Equal("XXXXXX", control.KeyDelta);
|
||||
Assert.Equal("XXXXXX", control.Reverse);
|
||||
Assert.Equal("XXXXXX", control.Ways);
|
||||
Assert.Equal("XXXXXX", control.Ways2);
|
||||
Assert.Equal("XXXXXX", control.Ways3);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipSwitch
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipSwitch? dipswitch)
|
||||
{
|
||||
Assert.NotNull(dipswitch);
|
||||
Assert.Equal("XXXXXX", dipswitch.Name);
|
||||
Assert.Equal("XXXXXX", dipswitch.Tag);
|
||||
Assert.Equal("XXXXXX", dipswitch.Mask);
|
||||
Validate(dipswitch.Condition);
|
||||
|
||||
Assert.NotNull(dipswitch.DipLocation);
|
||||
var diplocation = Assert.Single(dipswitch.DipLocation);
|
||||
Validate(diplocation);
|
||||
|
||||
Assert.NotNull(dipswitch.DipValue);
|
||||
var dipvalue = Assert.Single(dipswitch.DipValue);
|
||||
Validate(dipvalue);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Condition
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Condition? condition)
|
||||
{
|
||||
Assert.NotNull(condition);
|
||||
Assert.Equal("XXXXXX", condition.Tag);
|
||||
Assert.Equal("XXXXXX", condition.Mask);
|
||||
Assert.Equal("XXXXXX", condition.Relation);
|
||||
Assert.Equal("XXXXXX", condition.Value);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipLocation
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipLocation? diplocation)
|
||||
{
|
||||
Assert.NotNull(diplocation);
|
||||
Assert.Equal("XXXXXX", diplocation.Name);
|
||||
Assert.Equal("XXXXXX", diplocation.Number);
|
||||
Assert.Equal("XXXXXX", diplocation.Inverted);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipValue
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipValue? dipvalue)
|
||||
{
|
||||
Assert.NotNull(dipvalue);
|
||||
Assert.Equal("XXXXXX", dipvalue.Name);
|
||||
Assert.Equal("XXXXXX", dipvalue.Value);
|
||||
Assert.Equal("XXXXXX", dipvalue.Default);
|
||||
Validate(dipvalue.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Configuration
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Configuration? configuration)
|
||||
{
|
||||
Assert.NotNull(configuration);
|
||||
Assert.Equal("XXXXXX", configuration.Name);
|
||||
Assert.Equal("XXXXXX", configuration.Tag);
|
||||
Assert.Equal("XXXXXX", configuration.Mask);
|
||||
Validate(configuration.Condition);
|
||||
|
||||
Assert.NotNull(configuration.ConfLocation);
|
||||
var conflocation = Assert.Single(configuration.ConfLocation);
|
||||
Validate(conflocation);
|
||||
|
||||
Assert.NotNull(configuration.ConfSetting);
|
||||
var confsetting = Assert.Single(configuration.ConfSetting);
|
||||
Validate(confsetting);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ConfLocation
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.ConfLocation? conflocation)
|
||||
{
|
||||
Assert.NotNull(conflocation);
|
||||
Assert.Equal("XXXXXX", conflocation.Name);
|
||||
Assert.Equal("XXXXXX", conflocation.Number);
|
||||
Assert.Equal("XXXXXX", conflocation.Inverted);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ConfSetting
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.ConfSetting? confsetting)
|
||||
{
|
||||
Assert.NotNull(confsetting);
|
||||
Assert.Equal("XXXXXX", confsetting.Name);
|
||||
Assert.Equal("XXXXXX", confsetting.Value);
|
||||
Assert.Equal("XXXXXX", confsetting.Default);
|
||||
Validate(confsetting.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Port
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Port? port)
|
||||
{
|
||||
Assert.NotNull(port);
|
||||
Assert.Equal("XXXXXX", port.Tag);
|
||||
|
||||
Assert.NotNull(port.Analog);
|
||||
var analog = Assert.Single(port.Analog);
|
||||
Validate(analog);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Analog
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Analog? analog)
|
||||
{
|
||||
Assert.NotNull(analog);
|
||||
Assert.Equal("XXXXXX", analog.Mask);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Adjuster
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Adjuster? adjuster)
|
||||
{
|
||||
Assert.NotNull(adjuster);
|
||||
Assert.Equal("XXXXXX", adjuster.Name);
|
||||
Assert.Equal("XXXXXX", adjuster.Default);
|
||||
Validate(adjuster.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Driver
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Driver? driver)
|
||||
{
|
||||
Assert.NotNull(driver);
|
||||
Assert.Equal("XXXXXX", driver.Status);
|
||||
Assert.Equal("XXXXXX", driver.Color);
|
||||
Assert.Equal("XXXXXX", driver.Sound);
|
||||
Assert.Equal("XXXXXX", driver.PaletteSize);
|
||||
Assert.Equal("XXXXXX", driver.Emulation);
|
||||
Assert.Equal("XXXXXX", driver.Cocktail);
|
||||
Assert.Equal("XXXXXX", driver.SaveState);
|
||||
Assert.Equal("XXXXXX", driver.RequiresArtwork);
|
||||
Assert.Equal("XXXXXX", driver.Unofficial);
|
||||
Assert.Equal("XXXXXX", driver.NoSoundHardware);
|
||||
Assert.Equal("XXXXXX", driver.Incomplete);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Feature
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Feature? feature)
|
||||
{
|
||||
Assert.NotNull(feature);
|
||||
Assert.Equal("XXXXXX", feature.Type);
|
||||
Assert.Equal("XXXXXX", feature.Status);
|
||||
Assert.Equal("XXXXXX", feature.Overall);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Device
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Device? device)
|
||||
{
|
||||
Assert.NotNull(device);
|
||||
Assert.Equal("XXXXXX", device.Type);
|
||||
Assert.Equal("XXXXXX", device.Tag);
|
||||
Assert.Equal("XXXXXX", device.FixedImage);
|
||||
Assert.Equal("XXXXXX", device.Mandatory);
|
||||
Assert.Equal("XXXXXX", device.Interface);
|
||||
Validate(device.Instance);
|
||||
|
||||
Assert.NotNull(device.Extension);
|
||||
var extension = Assert.Single(device.Extension);
|
||||
Validate(extension);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Instance
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Instance? instance)
|
||||
{
|
||||
Assert.NotNull(instance);
|
||||
Assert.Equal("XXXXXX", instance.Name);
|
||||
Assert.Equal("XXXXXX", instance.BriefName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Extension
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Extension? extension)
|
||||
{
|
||||
Assert.NotNull(extension);
|
||||
Assert.Equal("XXXXXX", extension.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Slot
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Slot? slot)
|
||||
{
|
||||
Assert.NotNull(slot);
|
||||
Assert.Equal("XXXXXX", slot.Name);
|
||||
|
||||
Assert.NotNull(slot.SlotOption);
|
||||
var slotoption = Assert.Single(slot.SlotOption);
|
||||
Validate(slotoption);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SlotOption
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.SlotOption? slotoption)
|
||||
{
|
||||
Assert.NotNull(slotoption);
|
||||
Assert.Equal("XXXXXX", slotoption.Name);
|
||||
Assert.Equal("XXXXXX", slotoption.DevName);
|
||||
Assert.Equal("XXXXXX", slotoption.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SoftwareList
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.SoftwareList? softwarelist)
|
||||
{
|
||||
Assert.NotNull(softwarelist);
|
||||
Assert.Equal("XXXXXX", softwarelist.Tag);
|
||||
Assert.Equal("XXXXXX", softwarelist.Name);
|
||||
Assert.Equal("XXXXXX", softwarelist.Status);
|
||||
Assert.Equal("XXXXXX", softwarelist.Filter);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a RamOption
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.RamOption? ramoption)
|
||||
{
|
||||
Assert.NotNull(ramoption);
|
||||
Assert.Equal("XXXXXX", ramoption.Name);
|
||||
Assert.Equal("XXXXXX", ramoption.Default);
|
||||
Assert.Equal("XXXXXX", ramoption.Content);
|
||||
}
|
||||
}
|
||||
}
|
||||
872
SabreTools.Serialization.Test/CrossModel/MessTests.cs
Normal file
872
SabreTools.Serialization.Test/CrossModel/MessTests.cs
Normal file
@@ -0,0 +1,872 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class MessTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripGameTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Mess();
|
||||
|
||||
// Build the data
|
||||
Models.Listxml.Mess m1 = Build(game: true);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(m1);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listxml.Mess? newMess = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMess);
|
||||
Assert.Equal("XXXXXX", newMess.Version);
|
||||
|
||||
Assert.NotNull(newMess.Game);
|
||||
var newGame = Assert.Single(newMess.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RoundTripMachineTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.Mess();
|
||||
|
||||
// Build the data
|
||||
Models.Listxml.Mess m1 = Build(game: false);
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(m1);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.Listxml.Mess? newMess = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newMess);
|
||||
Assert.Equal("XXXXXX", newMess.Version);
|
||||
|
||||
Assert.NotNull(newMess.Game);
|
||||
var newGame = Assert.Single(newMess.Game);
|
||||
Validate(newGame);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.Listxml.Mess Build(bool game)
|
||||
{
|
||||
var biosset = new Models.Listxml.BiosSet
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Description = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var rom = new Models.Listxml.Rom
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Bios = "XXXXXX",
|
||||
Size = "XXXXXX",
|
||||
CRC = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Offset = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Optional = "XXXXXX",
|
||||
Dispose = "XXXXXX",
|
||||
SoundOnly = "XXXXXX",
|
||||
};
|
||||
|
||||
var disk = new Models.Listxml.Disk
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
MD5 = "XXXXXX",
|
||||
SHA1 = "XXXXXX",
|
||||
Merge = "XXXXXX",
|
||||
Region = "XXXXXX",
|
||||
Index = "XXXXXX",
|
||||
Writable = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Optional = "XXXXXX",
|
||||
};
|
||||
|
||||
var deviceref = new Models.Listxml.DeviceRef
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var sample = new Models.Listxml.Sample
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var chip = new Models.Listxml.Chip
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
SoundOnly = "XXXXXX",
|
||||
Clock = "XXXXXX",
|
||||
};
|
||||
|
||||
var display = new Models.Listxml.Display
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Type = "XXXXXX",
|
||||
Rotate = "XXXXXX",
|
||||
FlipX = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
Refresh = "XXXXXX",
|
||||
PixClock = "XXXXXX",
|
||||
HTotal = "XXXXXX",
|
||||
HBEnd = "XXXXXX",
|
||||
HBStart = "XXXXXX",
|
||||
VTotal = "XXXXXX",
|
||||
VBEnd = "XXXXXX",
|
||||
VBStart = "XXXXXX",
|
||||
};
|
||||
|
||||
var video = new Models.Listxml.Video
|
||||
{
|
||||
Screen = "XXXXXX",
|
||||
Orientation = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
AspectX = "XXXXXX",
|
||||
AspectY = "XXXXXX",
|
||||
Refresh = "XXXXXX",
|
||||
};
|
||||
|
||||
var sound = new Models.Listxml.Sound
|
||||
{
|
||||
Channels = "XXXXXX",
|
||||
};
|
||||
|
||||
var control = new Models.Listxml.Control
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Player = "XXXXXX",
|
||||
Buttons = "XXXXXX",
|
||||
ReqButtons = "XXXXXX",
|
||||
Minimum = "XXXXXX",
|
||||
Maximum = "XXXXXX",
|
||||
Sensitivity = "XXXXXX",
|
||||
KeyDelta = "XXXXXX",
|
||||
Reverse = "XXXXXX",
|
||||
Ways = "XXXXXX",
|
||||
Ways2 = "XXXXXX",
|
||||
Ways3 = "XXXXXX",
|
||||
};
|
||||
|
||||
var input = new Models.Listxml.Input
|
||||
{
|
||||
Service = "XXXXXX",
|
||||
Tilt = "XXXXXX",
|
||||
Players = "XXXXXX",
|
||||
//ControlAttr = "XXXXXX", // Mututally exclusive with input.Control
|
||||
Buttons = "XXXXXX",
|
||||
Coins = "XXXXXX",
|
||||
Control = [control],
|
||||
};
|
||||
|
||||
var condition = new Models.Listxml.Condition
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Relation = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
};
|
||||
|
||||
var diplocation = new Models.Listxml.DipLocation
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Number = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
};
|
||||
|
||||
var dipvalue = new Models.Listxml.DipValue
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var dipswitch = new Models.Listxml.DipSwitch
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Condition = condition,
|
||||
DipLocation = [diplocation],
|
||||
DipValue = [dipvalue],
|
||||
};
|
||||
|
||||
var conflocation = new Models.Listxml.ConfLocation
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Number = "XXXXXX",
|
||||
Inverted = "XXXXXX",
|
||||
};
|
||||
|
||||
var confsetting = new Models.Listxml.ConfSetting
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var configuration = new Models.Listxml.Configuration
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
Mask = "XXXXXX",
|
||||
Condition = condition,
|
||||
ConfLocation = [conflocation],
|
||||
ConfSetting = [confsetting],
|
||||
};
|
||||
|
||||
var analog = new Models.Listxml.Analog
|
||||
{
|
||||
Mask = "XXXXXX",
|
||||
};
|
||||
|
||||
var port = new Models.Listxml.Port
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Analog = [analog],
|
||||
};
|
||||
|
||||
var adjuster = new Models.Listxml.Adjuster
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Condition = condition,
|
||||
};
|
||||
|
||||
var driver = new Models.Listxml.Driver
|
||||
{
|
||||
Status = "XXXXXX",
|
||||
Color = "XXXXXX",
|
||||
Sound = "XXXXXX",
|
||||
PaletteSize = "XXXXXX",
|
||||
Emulation = "XXXXXX",
|
||||
Cocktail = "XXXXXX",
|
||||
SaveState = "XXXXXX",
|
||||
RequiresArtwork = "XXXXXX",
|
||||
Unofficial = "XXXXXX",
|
||||
NoSoundHardware = "XXXXXX",
|
||||
Incomplete = "XXXXXX",
|
||||
};
|
||||
|
||||
var feature = new Models.Listxml.Feature
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Overall = "XXXXXX",
|
||||
};
|
||||
|
||||
var instance = new Models.Listxml.Instance
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
BriefName = "XXXXXX",
|
||||
};
|
||||
|
||||
var extension = new Models.Listxml.Extension
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
};
|
||||
|
||||
var device = new Models.Listxml.Device
|
||||
{
|
||||
Type = "XXXXXX",
|
||||
Tag = "XXXXXX",
|
||||
FixedImage = "XXXXXX",
|
||||
Mandatory = "XXXXXX",
|
||||
Interface = "XXXXXX",
|
||||
Instance = instance,
|
||||
Extension = [extension],
|
||||
};
|
||||
|
||||
var slotOption = new Models.Listxml.SlotOption
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
DevName = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
};
|
||||
|
||||
var slot = new Models.Listxml.Slot
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
SlotOption = [slotOption],
|
||||
};
|
||||
|
||||
var softwarelist = new Models.Listxml.SoftwareList
|
||||
{
|
||||
Tag = "XXXXXX",
|
||||
Name = "XXXXXX",
|
||||
Status = "XXXXXX",
|
||||
Filter = "XXXXXX",
|
||||
};
|
||||
|
||||
var ramoption = new Models.Listxml.RamOption
|
||||
{
|
||||
Name = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Content = "XXXXXX",
|
||||
};
|
||||
|
||||
Models.Listxml.GameBase gameBase = game
|
||||
? new Models.Listxml.Game()
|
||||
: new Models.Listxml.Machine();
|
||||
gameBase.Name = "XXXXXX";
|
||||
gameBase.SourceFile = "XXXXXX";
|
||||
gameBase.IsBios = "XXXXXX";
|
||||
gameBase.IsDevice = "XXXXXX";
|
||||
gameBase.IsMechanical = "XXXXXX";
|
||||
gameBase.Runnable = "XXXXXX";
|
||||
gameBase.CloneOf = "XXXXXX";
|
||||
gameBase.RomOf = "XXXXXX";
|
||||
gameBase.SampleOf = "XXXXXX";
|
||||
gameBase.Description = "XXXXXX";
|
||||
gameBase.Year = "XXXXXX";
|
||||
gameBase.Manufacturer = "XXXXXX";
|
||||
gameBase.History = "XXXXXX";
|
||||
gameBase.BiosSet = [biosset];
|
||||
gameBase.Rom = [rom];
|
||||
gameBase.Disk = [disk];
|
||||
gameBase.DeviceRef = [deviceref];
|
||||
gameBase.Sample = [sample];
|
||||
gameBase.Chip = [chip];
|
||||
gameBase.Display = [display];
|
||||
gameBase.Video = [video];
|
||||
gameBase.Sound = sound;
|
||||
gameBase.Input = input;
|
||||
gameBase.DipSwitch = [dipswitch];
|
||||
gameBase.Configuration = [configuration];
|
||||
gameBase.Port = [port];
|
||||
gameBase.Adjuster = [adjuster];
|
||||
gameBase.Driver = driver;
|
||||
gameBase.Feature = [feature];
|
||||
gameBase.Device = [device];
|
||||
gameBase.Slot = [slot];
|
||||
gameBase.SoftwareList = [softwarelist];
|
||||
gameBase.RamOption = [ramoption];
|
||||
|
||||
return new Models.Listxml.Mess
|
||||
{
|
||||
Version = "XXXXXX",
|
||||
Game = [gameBase],
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a GameBase
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.GameBase? gb)
|
||||
{
|
||||
Assert.NotNull(gb);
|
||||
Assert.Equal("XXXXXX", gb.Name);
|
||||
Assert.Equal("XXXXXX", gb.SourceFile);
|
||||
Assert.Equal("XXXXXX", gb.IsBios);
|
||||
Assert.Equal("XXXXXX", gb.IsDevice);
|
||||
Assert.Equal("XXXXXX", gb.IsMechanical);
|
||||
Assert.Equal("XXXXXX", gb.Runnable);
|
||||
Assert.Equal("XXXXXX", gb.CloneOf);
|
||||
Assert.Equal("XXXXXX", gb.RomOf);
|
||||
Assert.Equal("XXXXXX", gb.SampleOf);
|
||||
Assert.Equal("XXXXXX", gb.Description);
|
||||
Assert.Equal("XXXXXX", gb.Year);
|
||||
Assert.Equal("XXXXXX", gb.Manufacturer);
|
||||
Assert.Equal("XXXXXX", gb.History);
|
||||
|
||||
Assert.NotNull(gb.BiosSet);
|
||||
var biosset = Assert.Single(gb.BiosSet);
|
||||
Validate(biosset);
|
||||
|
||||
Assert.NotNull(gb.Rom);
|
||||
var rom = Assert.Single(gb.Rom);
|
||||
Validate(rom);
|
||||
|
||||
Assert.NotNull(gb.Disk);
|
||||
var disk = Assert.Single(gb.Disk);
|
||||
Validate(disk);
|
||||
|
||||
Assert.NotNull(gb.DeviceRef);
|
||||
var deviceref = Assert.Single(gb.DeviceRef);
|
||||
Validate(deviceref);
|
||||
|
||||
Assert.NotNull(gb.Sample);
|
||||
var sample = Assert.Single(gb.Sample);
|
||||
Validate(sample);
|
||||
|
||||
Assert.NotNull(gb.Chip);
|
||||
var chip = Assert.Single(gb.Chip);
|
||||
Validate(chip);
|
||||
|
||||
Assert.NotNull(gb.Display);
|
||||
var display = Assert.Single(gb.Display);
|
||||
Validate(display);
|
||||
|
||||
Assert.NotNull(gb.Video);
|
||||
var video = Assert.Single(gb.Video);
|
||||
Validate(video);
|
||||
|
||||
Validate(gb.Sound);
|
||||
Validate(gb.Input);
|
||||
|
||||
Assert.NotNull(gb.DipSwitch);
|
||||
var dipswitch = Assert.Single(gb.DipSwitch);
|
||||
Validate(dipswitch);
|
||||
|
||||
Assert.NotNull(gb.Configuration);
|
||||
var configuration = Assert.Single(gb.Configuration);
|
||||
Validate(configuration);
|
||||
|
||||
Assert.NotNull(gb.Port);
|
||||
var port = Assert.Single(gb.Port);
|
||||
Validate(port);
|
||||
|
||||
Assert.NotNull(gb.Adjuster);
|
||||
var adjuster = Assert.Single(gb.Adjuster);
|
||||
Validate(adjuster);
|
||||
|
||||
Validate(gb.Driver);
|
||||
|
||||
Assert.NotNull(gb.Feature);
|
||||
var feature = Assert.Single(gb.Feature);
|
||||
Validate(feature);
|
||||
|
||||
Assert.NotNull(gb.Device);
|
||||
var device = Assert.Single(gb.Device);
|
||||
Validate(device);
|
||||
|
||||
Assert.NotNull(gb.Slot);
|
||||
var slot = Assert.Single(gb.Slot);
|
||||
Validate(slot);
|
||||
|
||||
Assert.NotNull(gb.SoftwareList);
|
||||
var softwarelist = Assert.Single(gb.SoftwareList);
|
||||
Validate(softwarelist);
|
||||
|
||||
Assert.NotNull(gb.RamOption);
|
||||
var ramoption = Assert.Single(gb.RamOption);
|
||||
Validate(ramoption);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a BiosSet
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.BiosSet? biosset)
|
||||
{
|
||||
Assert.NotNull(biosset);
|
||||
Assert.Equal("XXXXXX", biosset.Name);
|
||||
Assert.Equal("XXXXXX", biosset.Description);
|
||||
Assert.Equal("XXXXXX", biosset.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Rom
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Rom? rom)
|
||||
{
|
||||
Assert.NotNull(rom);
|
||||
Assert.Equal("XXXXXX", rom.Name);
|
||||
Assert.Equal("XXXXXX", rom.Bios);
|
||||
Assert.Equal("XXXXXX", rom.Size);
|
||||
Assert.Equal("XXXXXX", rom.CRC);
|
||||
Assert.Equal("XXXXXX", rom.SHA1);
|
||||
Assert.Equal("XXXXXX", rom.Merge);
|
||||
Assert.Equal("XXXXXX", rom.Region);
|
||||
Assert.Equal("XXXXXX", rom.Offset);
|
||||
Assert.Equal("XXXXXX", rom.Status);
|
||||
Assert.Equal("XXXXXX", rom.Optional);
|
||||
Assert.Equal("XXXXXX", rom.Dispose);
|
||||
Assert.Equal("XXXXXX", rom.SoundOnly);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Disk
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Disk? disk)
|
||||
{
|
||||
Assert.NotNull(disk);
|
||||
Assert.Equal("XXXXXX", disk.Name);
|
||||
Assert.Equal("XXXXXX", disk.MD5);
|
||||
Assert.Equal("XXXXXX", disk.SHA1);
|
||||
Assert.Equal("XXXXXX", disk.Merge);
|
||||
Assert.Equal("XXXXXX", disk.Region);
|
||||
Assert.Equal("XXXXXX", disk.Index);
|
||||
Assert.Equal("XXXXXX", disk.Writable);
|
||||
Assert.Equal("XXXXXX", disk.Status);
|
||||
Assert.Equal("XXXXXX", disk.Optional);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DeviceRef
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DeviceRef? deviceref)
|
||||
{
|
||||
Assert.NotNull(deviceref);
|
||||
Assert.Equal("XXXXXX", deviceref.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sample
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Sample? sample)
|
||||
{
|
||||
Assert.NotNull(sample);
|
||||
Assert.Equal("XXXXXX", sample.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Chip
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Chip? chip)
|
||||
{
|
||||
Assert.NotNull(chip);
|
||||
Assert.Equal("XXXXXX", chip.Name);
|
||||
Assert.Equal("XXXXXX", chip.Tag);
|
||||
Assert.Equal("XXXXXX", chip.Type);
|
||||
Assert.Equal("XXXXXX", chip.SoundOnly);
|
||||
Assert.Equal("XXXXXX", chip.Clock);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Display
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Display? display)
|
||||
{
|
||||
Assert.NotNull(display);
|
||||
Assert.Equal("XXXXXX", display.Tag);
|
||||
Assert.Equal("XXXXXX", display.Type);
|
||||
Assert.Equal("XXXXXX", display.Rotate);
|
||||
Assert.Equal("XXXXXX", display.FlipX);
|
||||
Assert.Equal("XXXXXX", display.Width);
|
||||
Assert.Equal("XXXXXX", display.Height);
|
||||
Assert.Equal("XXXXXX", display.Refresh);
|
||||
Assert.Equal("XXXXXX", display.PixClock);
|
||||
Assert.Equal("XXXXXX", display.HTotal);
|
||||
Assert.Equal("XXXXXX", display.HBEnd);
|
||||
Assert.Equal("XXXXXX", display.HBStart);
|
||||
Assert.Equal("XXXXXX", display.VTotal);
|
||||
Assert.Equal("XXXXXX", display.VBEnd);
|
||||
Assert.Equal("XXXXXX", display.VBStart);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Video
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Video? video)
|
||||
{
|
||||
Assert.NotNull(video);
|
||||
Assert.Equal("XXXXXX", video.Screen);
|
||||
Assert.Equal("XXXXXX", video.Orientation);
|
||||
Assert.Equal("XXXXXX", video.Width);
|
||||
Assert.Equal("XXXXXX", video.Height);
|
||||
Assert.Equal("XXXXXX", video.AspectX);
|
||||
Assert.Equal("XXXXXX", video.AspectY);
|
||||
Assert.Equal("XXXXXX", video.Refresh);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Sound
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Sound? sound)
|
||||
{
|
||||
Assert.NotNull(sound);
|
||||
Assert.Equal("XXXXXX", sound.Channels);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Input
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Input? input)
|
||||
{
|
||||
Assert.NotNull(input);
|
||||
Assert.Equal("XXXXXX", input.Service);
|
||||
Assert.Equal("XXXXXX", input.Tilt);
|
||||
Assert.Equal("XXXXXX", input.Players);
|
||||
//Assert.Equal("XXXXXX", input.ControlAttr); // Mututally exclusive with input.Control
|
||||
Assert.Equal("XXXXXX", input.Buttons);
|
||||
Assert.Equal("XXXXXX", input.Coins);
|
||||
|
||||
Assert.NotNull(input.Control);
|
||||
var control = Assert.Single(input.Control);
|
||||
Validate(control);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Control
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Control? control)
|
||||
{
|
||||
Assert.NotNull(control);
|
||||
Assert.Equal("XXXXXX", control.Type);
|
||||
Assert.Equal("XXXXXX", control.Player);
|
||||
Assert.Equal("XXXXXX", control.Buttons);
|
||||
Assert.Equal("XXXXXX", control.ReqButtons);
|
||||
Assert.Equal("XXXXXX", control.Minimum);
|
||||
Assert.Equal("XXXXXX", control.Maximum);
|
||||
Assert.Equal("XXXXXX", control.Sensitivity);
|
||||
Assert.Equal("XXXXXX", control.KeyDelta);
|
||||
Assert.Equal("XXXXXX", control.Reverse);
|
||||
Assert.Equal("XXXXXX", control.Ways);
|
||||
Assert.Equal("XXXXXX", control.Ways2);
|
||||
Assert.Equal("XXXXXX", control.Ways3);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipSwitch
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipSwitch? dipswitch)
|
||||
{
|
||||
Assert.NotNull(dipswitch);
|
||||
Assert.Equal("XXXXXX", dipswitch.Name);
|
||||
Assert.Equal("XXXXXX", dipswitch.Tag);
|
||||
Assert.Equal("XXXXXX", dipswitch.Mask);
|
||||
Validate(dipswitch.Condition);
|
||||
|
||||
Assert.NotNull(dipswitch.DipLocation);
|
||||
var diplocation = Assert.Single(dipswitch.DipLocation);
|
||||
Validate(diplocation);
|
||||
|
||||
Assert.NotNull(dipswitch.DipValue);
|
||||
var dipvalue = Assert.Single(dipswitch.DipValue);
|
||||
Validate(dipvalue);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Condition
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Condition? condition)
|
||||
{
|
||||
Assert.NotNull(condition);
|
||||
Assert.Equal("XXXXXX", condition.Tag);
|
||||
Assert.Equal("XXXXXX", condition.Mask);
|
||||
Assert.Equal("XXXXXX", condition.Relation);
|
||||
Assert.Equal("XXXXXX", condition.Value);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipLocation
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipLocation? diplocation)
|
||||
{
|
||||
Assert.NotNull(diplocation);
|
||||
Assert.Equal("XXXXXX", diplocation.Name);
|
||||
Assert.Equal("XXXXXX", diplocation.Number);
|
||||
Assert.Equal("XXXXXX", diplocation.Inverted);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DipValue
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.DipValue? dipvalue)
|
||||
{
|
||||
Assert.NotNull(dipvalue);
|
||||
Assert.Equal("XXXXXX", dipvalue.Name);
|
||||
Assert.Equal("XXXXXX", dipvalue.Value);
|
||||
Assert.Equal("XXXXXX", dipvalue.Default);
|
||||
Validate(dipvalue.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Configuration
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Configuration? configuration)
|
||||
{
|
||||
Assert.NotNull(configuration);
|
||||
Assert.Equal("XXXXXX", configuration.Name);
|
||||
Assert.Equal("XXXXXX", configuration.Tag);
|
||||
Assert.Equal("XXXXXX", configuration.Mask);
|
||||
Validate(configuration.Condition);
|
||||
|
||||
Assert.NotNull(configuration.ConfLocation);
|
||||
var conflocation = Assert.Single(configuration.ConfLocation);
|
||||
Validate(conflocation);
|
||||
|
||||
Assert.NotNull(configuration.ConfSetting);
|
||||
var confsetting = Assert.Single(configuration.ConfSetting);
|
||||
Validate(confsetting);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ConfLocation
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.ConfLocation? conflocation)
|
||||
{
|
||||
Assert.NotNull(conflocation);
|
||||
Assert.Equal("XXXXXX", conflocation.Name);
|
||||
Assert.Equal("XXXXXX", conflocation.Number);
|
||||
Assert.Equal("XXXXXX", conflocation.Inverted);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a ConfSetting
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.ConfSetting? confsetting)
|
||||
{
|
||||
Assert.NotNull(confsetting);
|
||||
Assert.Equal("XXXXXX", confsetting.Name);
|
||||
Assert.Equal("XXXXXX", confsetting.Value);
|
||||
Assert.Equal("XXXXXX", confsetting.Default);
|
||||
Validate(confsetting.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Port
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Port? port)
|
||||
{
|
||||
Assert.NotNull(port);
|
||||
Assert.Equal("XXXXXX", port.Tag);
|
||||
|
||||
Assert.NotNull(port.Analog);
|
||||
var analog = Assert.Single(port.Analog);
|
||||
Validate(analog);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Analog
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Analog? analog)
|
||||
{
|
||||
Assert.NotNull(analog);
|
||||
Assert.Equal("XXXXXX", analog.Mask);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Adjuster
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Adjuster? adjuster)
|
||||
{
|
||||
Assert.NotNull(adjuster);
|
||||
Assert.Equal("XXXXXX", adjuster.Name);
|
||||
Assert.Equal("XXXXXX", adjuster.Default);
|
||||
Validate(adjuster.Condition);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Driver
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Driver? driver)
|
||||
{
|
||||
Assert.NotNull(driver);
|
||||
Assert.Equal("XXXXXX", driver.Status);
|
||||
Assert.Equal("XXXXXX", driver.Color);
|
||||
Assert.Equal("XXXXXX", driver.Sound);
|
||||
Assert.Equal("XXXXXX", driver.PaletteSize);
|
||||
Assert.Equal("XXXXXX", driver.Emulation);
|
||||
Assert.Equal("XXXXXX", driver.Cocktail);
|
||||
Assert.Equal("XXXXXX", driver.SaveState);
|
||||
Assert.Equal("XXXXXX", driver.RequiresArtwork);
|
||||
Assert.Equal("XXXXXX", driver.Unofficial);
|
||||
Assert.Equal("XXXXXX", driver.NoSoundHardware);
|
||||
Assert.Equal("XXXXXX", driver.Incomplete);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Feature
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Feature? feature)
|
||||
{
|
||||
Assert.NotNull(feature);
|
||||
Assert.Equal("XXXXXX", feature.Type);
|
||||
Assert.Equal("XXXXXX", feature.Status);
|
||||
Assert.Equal("XXXXXX", feature.Overall);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Device
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Device? device)
|
||||
{
|
||||
Assert.NotNull(device);
|
||||
Assert.Equal("XXXXXX", device.Type);
|
||||
Assert.Equal("XXXXXX", device.Tag);
|
||||
Assert.Equal("XXXXXX", device.FixedImage);
|
||||
Assert.Equal("XXXXXX", device.Mandatory);
|
||||
Assert.Equal("XXXXXX", device.Interface);
|
||||
Validate(device.Instance);
|
||||
|
||||
Assert.NotNull(device.Extension);
|
||||
var extension = Assert.Single(device.Extension);
|
||||
Validate(extension);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Instance
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Instance? instance)
|
||||
{
|
||||
Assert.NotNull(instance);
|
||||
Assert.Equal("XXXXXX", instance.Name);
|
||||
Assert.Equal("XXXXXX", instance.BriefName);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Extension
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Extension? extension)
|
||||
{
|
||||
Assert.NotNull(extension);
|
||||
Assert.Equal("XXXXXX", extension.Name);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Slot
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.Slot? slot)
|
||||
{
|
||||
Assert.NotNull(slot);
|
||||
Assert.Equal("XXXXXX", slot.Name);
|
||||
|
||||
Assert.NotNull(slot.SlotOption);
|
||||
var slotoption = Assert.Single(slot.SlotOption);
|
||||
Validate(slotoption);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SlotOption
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.SlotOption? slotoption)
|
||||
{
|
||||
Assert.NotNull(slotoption);
|
||||
Assert.Equal("XXXXXX", slotoption.Name);
|
||||
Assert.Equal("XXXXXX", slotoption.DevName);
|
||||
Assert.Equal("XXXXXX", slotoption.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a SoftwareList
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.SoftwareList? softwarelist)
|
||||
{
|
||||
Assert.NotNull(softwarelist);
|
||||
Assert.Equal("XXXXXX", softwarelist.Tag);
|
||||
Assert.Equal("XXXXXX", softwarelist.Name);
|
||||
Assert.Equal("XXXXXX", softwarelist.Status);
|
||||
Assert.Equal("XXXXXX", softwarelist.Filter);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a RamOption
|
||||
/// </summary>
|
||||
private static void Validate(Models.Listxml.RamOption? ramoption)
|
||||
{
|
||||
Assert.NotNull(ramoption);
|
||||
Assert.Equal("XXXXXX", ramoption.Name);
|
||||
Assert.Equal("XXXXXX", ramoption.Default);
|
||||
Assert.Equal("XXXXXX", ramoption.Content);
|
||||
}
|
||||
}
|
||||
}
|
||||
450
SabreTools.Serialization.Test/CrossModel/OfflineListTests.cs
Normal file
450
SabreTools.Serialization.Test/CrossModel/OfflineListTests.cs
Normal file
@@ -0,0 +1,450 @@
|
||||
using Xunit;
|
||||
|
||||
namespace SabreTools.Serialization.Test.CrossModel
|
||||
{
|
||||
public class OfflineListTests
|
||||
{
|
||||
[Fact]
|
||||
public void RoundTripTest()
|
||||
{
|
||||
// Get the cross-model serializer
|
||||
var serializer = new Serialization.CrossModel.OfflineList();
|
||||
|
||||
// Build the data
|
||||
Models.OfflineList.Dat dat = Build();
|
||||
|
||||
// Serialize to generic model
|
||||
Models.Metadata.MetadataFile? metadata = serializer.Serialize(dat);
|
||||
Assert.NotNull(metadata);
|
||||
|
||||
// Serialize back to original model
|
||||
Models.OfflineList.Dat? newDat = serializer.Deserialize(metadata);
|
||||
|
||||
// Validate the data
|
||||
Assert.NotNull(newDat);
|
||||
Assert.Equal("XXXXXX", newDat.NoNamespaceSchemaLocation);
|
||||
Validate(newDat.Configuration);
|
||||
Validate(newDat.Games);
|
||||
Validate(newDat.GUI);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Build model for serialization and deserialization
|
||||
/// </summary>
|
||||
private static Models.OfflineList.Dat Build()
|
||||
{
|
||||
var infos = new Models.OfflineList.Infos
|
||||
{
|
||||
Title = new Models.OfflineList.Title
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
Location = new Models.OfflineList.Location
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
Publisher = new Models.OfflineList.Publisher
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
SourceRom = new Models.OfflineList.SourceRom
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
SaveType = new Models.OfflineList.SaveType
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
RomSize = new Models.OfflineList.RomSize
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
ReleaseNumber = new Models.OfflineList.ReleaseNumber
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
ImageNumber = new Models.OfflineList.ImageNumber
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
LanguageNumber = new Models.OfflineList.LanguageNumber
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
Comment = new Models.OfflineList.Comment
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
RomCRC = new Models.OfflineList.RomCRC
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
Im1CRC = new Models.OfflineList.Im1CRC
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
Im2CRC = new Models.OfflineList.Im2CRC
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
Languages = new Models.OfflineList.Languages
|
||||
{
|
||||
Visible = "XXXXXX",
|
||||
InNamingOption = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
},
|
||||
};
|
||||
|
||||
var canopen = new Models.OfflineList.CanOpen
|
||||
{
|
||||
Extension = ["XXXXXX"],
|
||||
};
|
||||
|
||||
var daturl = new Models.OfflineList.DatUrl
|
||||
{
|
||||
FileName = "XXXXXX",
|
||||
Content = "XXXXXX",
|
||||
};
|
||||
|
||||
var newdat = new Models.OfflineList.NewDat
|
||||
{
|
||||
DatVersionUrl = "XXXXXX",
|
||||
DatUrl = daturl,
|
||||
ImUrl = "XXXXXX",
|
||||
};
|
||||
|
||||
var find = new Models.OfflineList.Find
|
||||
{
|
||||
Operation = "XXXXXX",
|
||||
Value = "XXXXXX",
|
||||
Content = "XXXXXX",
|
||||
};
|
||||
|
||||
var to = new Models.OfflineList.To
|
||||
{
|
||||
Value = "XXXXXX",
|
||||
Default = "XXXXXX",
|
||||
Auto = "XXXXXX",
|
||||
Find = [find],
|
||||
};
|
||||
|
||||
var search = new Models.OfflineList.Search
|
||||
{
|
||||
To = [to],
|
||||
};
|
||||
|
||||
var configuration = new Models.OfflineList.Configuration
|
||||
{
|
||||
DatName = "XXXXXX",
|
||||
ImFolder = "XXXXXX",
|
||||
DatVersion = "XXXXXX",
|
||||
System = "XXXXXX",
|
||||
ScreenshotsWidth = "XXXXXX",
|
||||
ScreenshotsHeight = "XXXXXX",
|
||||
Infos = infos,
|
||||
CanOpen = canopen,
|
||||
NewDat = newdat,
|
||||
Search = search,
|
||||
RomTitle = "XXXXXX",
|
||||
};
|
||||
|
||||
var fileromcrc = new Models.OfflineList.FileRomCRC
|
||||
{
|
||||
Extension = "XXXXXX",
|
||||
Content = "XXXXXX",
|
||||
};
|
||||
|
||||
var files = new Models.OfflineList.Files
|
||||
{
|
||||
RomCRC = [fileromcrc],
|
||||
};
|
||||
|
||||
var game = new Models.OfflineList.Game
|
||||
{
|
||||
ImageNumber = "XXXXXX",
|
||||
ReleaseNumber = "XXXXXX",
|
||||
Title = "XXXXXX",
|
||||
SaveType = "XXXXXX",
|
||||
RomSize = "XXXXXX",
|
||||
Publisher = "XXXXXX",
|
||||
Location = "XXXXXX",
|
||||
SourceRom = "XXXXXX",
|
||||
Language = "XXXXXX",
|
||||
Files = files,
|
||||
Im1CRC = "XXXXXX",
|
||||
Im2CRC = "XXXXXX",
|
||||
Comment = "XXXXXX",
|
||||
DuplicateID = "XXXXXX",
|
||||
};
|
||||
|
||||
var games = new Models.OfflineList.Games
|
||||
{
|
||||
Game = [game],
|
||||
};
|
||||
|
||||
var image = new Models.OfflineList.Image
|
||||
{
|
||||
X = "XXXXXX",
|
||||
Y = "XXXXXX",
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
};
|
||||
|
||||
var images = new Models.OfflineList.Images
|
||||
{
|
||||
Width = "XXXXXX",
|
||||
Height = "XXXXXX",
|
||||
Image = [image],
|
||||
};
|
||||
|
||||
var gui = new Models.OfflineList.GUI
|
||||
{
|
||||
Images = images,
|
||||
};
|
||||
|
||||
return new Models.OfflineList.Dat
|
||||
{
|
||||
NoNamespaceSchemaLocation = "XXXXXX",
|
||||
Configuration = configuration,
|
||||
Games = games,
|
||||
GUI = gui,
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Configuration
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Configuration? configuration)
|
||||
{
|
||||
Assert.NotNull(configuration);
|
||||
Assert.Equal("XXXXXX", configuration.DatName);
|
||||
Assert.Equal("XXXXXX", configuration.ImFolder);
|
||||
Assert.Equal("XXXXXX", configuration.DatVersion);
|
||||
Assert.Equal("XXXXXX", configuration.System);
|
||||
Assert.Equal("XXXXXX", configuration.ScreenshotsWidth);
|
||||
Assert.Equal("XXXXXX", configuration.ScreenshotsHeight);
|
||||
Validate(configuration.Infos);
|
||||
Validate(configuration.CanOpen);
|
||||
Validate(configuration.NewDat);
|
||||
Validate(configuration.Search);
|
||||
Assert.Equal("XXXXXX", configuration.RomTitle);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Infos
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Infos? infos)
|
||||
{
|
||||
Assert.NotNull(infos);
|
||||
Validate(infos.Title);
|
||||
Validate(infos.Location);
|
||||
Validate(infos.Publisher);
|
||||
Validate(infos.SourceRom);
|
||||
Validate(infos.SaveType);
|
||||
Validate(infos.RomSize);
|
||||
Validate(infos.ReleaseNumber);
|
||||
Validate(infos.ImageNumber);
|
||||
Validate(infos.LanguageNumber);
|
||||
Validate(infos.Comment);
|
||||
Validate(infos.RomCRC);
|
||||
Validate(infos.Im1CRC);
|
||||
Validate(infos.Im2CRC);
|
||||
Validate(infos.Languages);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a InfoBase
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.InfoBase? info)
|
||||
{
|
||||
Assert.NotNull(info);
|
||||
Assert.Equal("XXXXXX", info.Visible);
|
||||
Assert.Equal("XXXXXX", info.InNamingOption);
|
||||
Assert.Equal("XXXXXX", info.Default);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a CanOpen
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.CanOpen? canopen)
|
||||
{
|
||||
Assert.NotNull(canopen);
|
||||
Assert.NotNull(canopen.Extension);
|
||||
string extension = Assert.Single(canopen.Extension);
|
||||
Assert.Equal("XXXXXX", extension);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a NewDat
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.NewDat? newdat)
|
||||
{
|
||||
Assert.NotNull(newdat);
|
||||
Assert.Equal("XXXXXX", newdat.DatVersionUrl);
|
||||
Validate(newdat.DatUrl);
|
||||
Assert.Equal("XXXXXX", newdat.ImUrl);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a DatUrl
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.DatUrl? daturl)
|
||||
{
|
||||
Assert.NotNull(daturl);
|
||||
Assert.Equal("XXXXXX", daturl.FileName);
|
||||
Assert.Equal("XXXXXX", daturl.Content);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Search
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Search? search)
|
||||
{
|
||||
Assert.NotNull(search);
|
||||
Assert.NotNull(search.To);
|
||||
var to = Assert.Single(search.To);
|
||||
Validate(to);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a To
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.To? to)
|
||||
{
|
||||
Assert.NotNull(to);
|
||||
Assert.Equal("XXXXXX", to.Value);
|
||||
Assert.Equal("XXXXXX", to.Default);
|
||||
Assert.Equal("XXXXXX", to.Auto);
|
||||
|
||||
Assert.NotNull(to.Find);
|
||||
var find = Assert.Single(to.Find);
|
||||
Validate(find);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Find
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Find? find)
|
||||
{
|
||||
Assert.NotNull(find);
|
||||
Assert.Equal("XXXXXX", find.Operation);
|
||||
Assert.Equal("XXXXXX", find.Value);
|
||||
Assert.Equal("XXXXXX", find.Content);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Games
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Games? games)
|
||||
{
|
||||
Assert.NotNull(games);
|
||||
Assert.NotNull(games.Game);
|
||||
var game = Assert.Single(games.Game);
|
||||
Validate(game);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Game
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Game? game)
|
||||
{
|
||||
Assert.NotNull(game);
|
||||
Assert.Equal("XXXXXX", game.ImageNumber);
|
||||
Assert.Equal("XXXXXX", game.ReleaseNumber);
|
||||
Assert.Equal("XXXXXX", game.Title);
|
||||
Assert.Equal("XXXXXX", game.SaveType);
|
||||
Assert.Equal("0", game.RomSize); // Converted due to filtering
|
||||
Assert.Equal("XXXXXX", game.Publisher);
|
||||
Assert.Equal("XXXXXX", game.Location);
|
||||
Assert.Equal("XXXXXX", game.SourceRom);
|
||||
Assert.Equal("XXXXXX", game.Language);
|
||||
Validate(game.Files);
|
||||
Assert.Equal("XXXXXX", game.Im1CRC);
|
||||
Assert.Equal("XXXXXX", game.Im2CRC);
|
||||
Assert.Equal("XXXXXX", game.Comment);
|
||||
Assert.Equal("XXXXXX", game.DuplicateID);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Files
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Files? files)
|
||||
{
|
||||
Assert.NotNull(files);
|
||||
Assert.NotNull(files.RomCRC);
|
||||
var fileromcrc = Assert.Single(files.RomCRC);
|
||||
Validate(fileromcrc);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a FileRomCRC
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.FileRomCRC? fileromcrc)
|
||||
{
|
||||
Assert.NotNull(fileromcrc);
|
||||
Assert.Equal("XXXXXX", fileromcrc.Extension);
|
||||
Assert.Equal("XXXXXX", fileromcrc.Content);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a GUI
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.GUI? gui)
|
||||
{
|
||||
Assert.NotNull(gui);
|
||||
Validate(gui.Images);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Images
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Images? images)
|
||||
{
|
||||
Assert.NotNull(images);
|
||||
Assert.Equal("XXXXXX", images.Width);
|
||||
Assert.Equal("XXXXXX", images.Height);
|
||||
|
||||
Assert.NotNull(images.Image);
|
||||
var image = Assert.Single(images.Image);
|
||||
Validate(image);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Validate a Image
|
||||
/// </summary>
|
||||
private static void Validate(Models.OfflineList.Image? image)
|
||||
{
|
||||
Assert.NotNull(image);
|
||||
Assert.Equal("XXXXXX", image.X);
|
||||
Assert.Equal("XXXXXX", image.Y);
|
||||
Assert.Equal("XXXXXX", image.Width);
|
||||
Assert.Equal("XXXXXX", image.Height);
|
||||
}
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user