-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathFlux.cpp
More file actions
126 lines (117 loc) · 3.71 KB
/
Copy pathFlux.cpp
File metadata and controls
126 lines (117 loc) · 3.71 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
// SPDX-License-Identifier: GPL-3.0-or-later
// Copyright (C) 2026 Daniele Terdina
#include "MdvDecode.h"
void RemoveSpurious(vector<BYTE>& data, int maxSpuriousLen, BYTE trackMask)
{
size_t lastTriggerTime = 0;
size_t spuriousStart = 0;
size_t spuriousEnd = 0;
int numSpurious = 0;
for (size_t i = 1; i < data.size(); i++)
{
BYTE trigger = (data[i] ^ data[i - 1]) & trackMask;
if (trigger)
{
if (i - lastTriggerTime <= maxSpuriousLen && lastTriggerTime != 0)
{
if (!numSpurious)
spuriousStart = lastTriggerTime;
numSpurious++;
spuriousEnd = i;
}
else if (numSpurious)
{
BYTE prevValue = (data[spuriousStart] & trackMask) ^ trackMask;
if (numSpurious & 1)
{
for (size_t j = spuriousStart; j < spuriousEnd; j++)
data[j] = (data[j] & ~trackMask) | prevValue;
}
else
{
size_t mid = (spuriousEnd + spuriousStart) / 2;
for (size_t j = spuriousStart; j < spuriousEnd; j++)
{
if (j == mid)
prevValue = prevValue ^ trackMask;
data[j] = (data[j] & ~trackMask) | prevValue;
}
}
numSpurious = 0;
}
lastTriggerTime = i;
}
}
}
vector<Chunk> FluxChunks(const vector<BYTE>& data, int minGapLen, BYTE track1Mask, BYTE track2Mask)
{
vector<Chunk> chunkList;
Chunk chunk;
size_t lastCh1 = 0;
size_t lastCh2 = 0;
size_t last = 0;
size_t chunkStart = 0;
BYTE prev = data[0];
bool firstEvent = true;
chunk.gapLen = 0;
BYTE tracksMask = track1Mask | track2Mask;
for (size_t i = 0; i < data.size(); i++)
{
BYTE b = data[i];
BYTE trigger = (b ^ prev) & tracksMask;
prev = b;
if (trigger)
{
if (firstEvent || i - last >= minGapLen)
{
// We look for gaps present in both tracks, but maybe the ZX8302 only uses track1?
if (!chunk.track1.empty() || !chunk.track2.empty())
{
chunk.dataLen = last - chunkStart;
chunkList.push_back(chunk);
chunk.gapLen = 0;
}
else
{
// Example: two gaps with single isolated transition in-between
// Gap len will be added
int xx = 0;
}
chunk.gapLen += i - last;
chunkStart = i;
last = lastCh1 = lastCh2 = i;
chunk.track1.clear();
chunk.track2.clear();
firstEvent = false;
}
else
{
last = i;
if (trigger & track1Mask)
{
chunk.track1.push_back(i - lastCh1);
lastCh1 = last;
}
if (trigger & track2Mask)
{
chunk.track2.push_back(i - lastCh2);
lastCh2 = last;
}
}
}
}
if (!chunk.track1.empty() || !chunk.track2.empty())
{
chunk.dataLen = data.size() - chunkStart;
chunkList.push_back(chunk);
}
if (data.size() - last >= minGapLen)
{
chunk.gapLen = data.size() - last;
chunk.dataLen = 0;
chunk.track1.clear();
chunk.track2.clear();
chunkList.push_back(chunk);
}
return chunkList;
}